40 character*40 :: field, timetag, depth, varname
41 character*128 :: dir_in, dir_out
42 character*256 :: file_in, file_out
43 integer :: nargs,iargc
45 integer :: idm, jdm,idm_out,jdm_out,ddim
46 integer :: i,ii,ip,j,jj,jp
47 integer :: if_sm,il_sm,jf_sm,jl_sm
48 integer :: status,ncid,ncid2,vid
49 integer :: latid, lonid, depthid
50 integer :: varid, xoutid, youtid
51 real,
allocatable :: lats(:), lons(:), dep(:)
52 character*80 :: attstr
53 integer :: start_3d(4),count_3d(4)
55 integer,
allocatable :: m_sm(:,:), iv_sm(:,:)
56 integer,
allocatable :: m_out(:,:), m_osm(:,:)
57 real,
allocatable :: a_in(:,:)
58 real,
allocatable,
target :: a_out(:,:)
60 integer,
allocatable :: i_out(:,:),j_out(:,:)
61 real,
allocatable :: x_out(:,:),y_out(:,:)
63 real,
parameter :: spval=2.0**100
64 real,
parameter :: hspval=0.5*2.0**100
66 logical :: file_exists
67 integer :: count, count1
69 INTEGER(HID_T) :: file_id
70 INTEGER(HID_T) :: dset_id
72 INTEGER(HSIZE_T),
DIMENSION(2) :: dims_sal
73 INTEGER(HSIZE_T),
DIMENSION(3) :: offset=(/0,0,0/)
74 INTEGER(HID_T) :: filespace
75 INTEGER(HID_T) :: dataspace
76 real(4),
POINTER :: pt
81 include
"aquarius.fin"
86 idm_out=1440;jdm_out=720
92 call getarg(1,file_in)
93 call getarg(2,dir_out)
97 &
"Command:get_hycom [temp|salt] infile outdir"
105 slash_pos =
index(file_in,
'/',back=.true.)
106 timetag = file_in(slash_pos+7:slash_pos+10)//file_in(slash_pos+12:slash_pos
108 if (field .eq.
"temp")
then
109 varname=
"temperature"
110 elseif (field .eq.
"salt")
then
113 print *,
"field has to be either temp or salt"
118 if (depth .eq.
'0') level=1
119 if (depth .eq.
'10') level=2
120 if (depth .eq.
'20') level=3
121 if (depth .eq.
'30') level=4
122 if (depth .eq.
'50') level=5
123 if (depth .eq.
'100') level=6
124 if (depth .eq.
'250') level=7
125 if (depth .eq.
'500') level=8
126 if (depth .eq.
'1000') level=9
128 print *,
"depth value is invalid"
133 allocate( iv_sm(jdm,2) )
135 allocate( m_sm(idm,jdm), m_osm(idm_out,jdm_out) )
136 allocate( m_out(idm_out,jdm_out) )
137 allocate( a_in(idm,jdm), a_out(idm_out,jdm_out) )
139 allocate( i_out(idm_out,jdm_out), j_out(idm_out,jdm_out) )
140 allocate( x_out(idm_out,jdm_out), y_out(idm_out,jdm_out) )
146 call getenv(
'OCDATAROOT', datadir)
149 status=nf90_open(
trim(datadir)//
'/aquarius/static/hycom_landmask.nc'
150 if (status /= nf90_noerr)
then
151 write(*,*)
'Land mask "hycom_landmask.nc" cannot be opened.'
155 status=nf90_inq_varid(ncid,
"mask",vid)
156 if (status /= nf90_noerr)
then
160 status=nf90_get_var(ncid,vid,m_out)
161 if (status /= nf90_noerr)
then
165 status=nf90_close(ncid)
170 inquire(file=file_in, exist=file_exists)
171 if (.not. file_exists)
then
172 print *, file_in,
" does not exist"
179 file_out=
trim(dir_out)//
'/N'//
trim(timetag)//
'00_SALINITY_HYCOM_24h.nc'
184 status=nf90_create(file_out,0, ncid)
185 if (status /= nf90_noerr)
then
186 write(*,*)
'NetCDF output file cannot be created.'
190 status=nf90_def_dim(ncid,
'lat', jdm_out, latid)
191 if (status /= nf90_noerr)
call handle_err(status)
192 status=nf90_def_dim(ncid,
'lon', idm_out, lonid)
193 if (status /= nf90_noerr)
call handle_err(status)
195 status=nf90_def_var(ncid,
'salt', nf90_float,
196 & (/lonid,latid/), varid)
197 if (status /= nf90_noerr)
call handle_err(status)
199 status=nf90_put_att(ncid,varid,
'long_name',attstr)
201 status=nf90_put_att(ncid,varid,
'units',attstr)
202 if (status /= nf90_noerr)
call handle_err(status)
203 status=nf90_put_att(ncid,varid,
'_FillValue',spval)
204 if (status /= nf90_noerr)
call handle_err(status)
205 status=nf90_enddef(ncid)
206 if (status /= nf90_noerr)
call handle_err(status)
208 allocate(lats(jdm_out), lons(idm_out), dep(ddim))
211 lons(i)=-180.125+i*0.25
214 lats(i)=-90.125+i*0.25
216 dep(1)=0; dep(2)=10; dep(3)=20; dep(4)=30
217 dep(5)=50; dep(6)=100; dep(7)=250; dep(8)=500
220 deallocate(lats,lons,dep)
224 status=nf90_open(file_in, nf90_nowrite, ncid)
225 if (status /= nf90_noerr)
call handle_err(status)
226 status=nf90_inq_varid(ncid,varname,vid)
227 status=nf90_get_var(ncid,vid,a_in)
228 if (status /= nf90_noerr)
call handle_err(status)
229 status=nf90_close(ncid)
230 if (status /= nf90_noerr)
call handle_err(status)
235 if (a_in(i,j).gt.hspval)
then
243 print *,
"hspval", hspval
244 print *,
"Input data ", count,
" land point"
248 status=nf90_open(
trim(datadir)//
'/aquarius/static/hycom_weight.nc'
250 if (status /= nf90_noerr)
then
251 write(*,*)
'HYCOM weight file "hycom_weight.nc" cannot be opened.'
255 status=nf90_inq_varid(ncid,
'x_out', xoutid)
256 if (status /= nf90_noerr)
call handle_err(status)
257 status=nf90_inq_varid(ncid,
'y_out', youtid)
258 if (status /= nf90_noerr)
call handle_err(status)
259 status=nf90_get_var(ncid,xoutid,x_out)
260 if (status /= nf90_noerr)
call handle_err(status)
261 status=nf90_get_var(ncid,youtid,y_out)
262 if (status /= nf90_noerr)
call handle_err(status)
263 status=nf90_close(ncid)
264 if (status /= nf90_noerr)
call handle_err(status)
269 if (x_out(ii,jj).lt.hspval)
then
270 i_out(ii,jj) = int(x_out(ii,jj))
271 x_out(ii,jj) = x_out(ii,jj) - i_out(ii,jj)
272 j_out(ii,jj) = int(y_out(ii,jj))
273 y_out(ii,jj) = y_out(ii,jj) - j_out(ii,jj)
291 if (m_out(ii,jj).eq.1)
then
300 if (m_sm(i,j).eq.0)
then
304 if (m_sm(i,jp).eq.0)
then
308 if (m_sm(ip,j).eq.0)
then
312 if (m_sm(ip,jp).eq.0)
then
316 if (count > 0) count1=count1+1
321 print *,
"Total ", count1,
"ocean point hits land"
326 if (m_sm(i,j).eq.2)
then
332 do i= idm,iv_sm(j,1),-1
333 if (m_sm(i,j).eq.2)
then
341 if (iv_sm(j,1).le.iv_sm(j,2))
then
348 if (iv_sm(j,1).le.iv_sm(j,2))
then
353 if_sm = minval(iv_sm(:,1))
354 il_sm = maxval(iv_sm(:,2))
357 & iv_sm,if_sm,il_sm,jf_sm,jl_sm)
359 & a_out, idm_out,jdm_out,
360 & m_sm, m_out,i_out,j_out,x_out,y_out)
364 status = nf90_open(file_out,nf90_write,ncid2)
365 if (status /= nf90_noerr)
call handle_err(status)
372 status=nf90_inq_varid(ncid2,field,vid)
373 if (status /= nf90_noerr)
call handle_err(status)
374 status=nf90_put_var(ncid2, vid,a_out,
375 & start=start_3d,count=count_3d)
376 if (status /= nf90_noerr)
call handle_err(status)
377 status=nf90_close(ncid2)
378 if (status /= nf90_noerr)
call handle_err(status)
384 if (a_out(i,j) .eq. spval)
then
393 file_out=
trim(dir_out)//
'/N'//
trim(timetag)//
'00_SALINITY_HYCOM_24h.h5'
395 call create_hdf5(file_out, file_id)
401 call create_hdf5_real(file_id,
'salinity', rank, dims_sal, dset_id
402 call set_space_hdf5(dset_id, rank, dims_sal, filespace, dataspace)
404 call write_hdf5_real(dset_id, filespace, dataspace, offset, dims_sal
405 call close_hdf5_ds(dset_id, dataspace, filespace)
406 call close_hdf5_df(file_id)
410 file_out=
trim(dir_out)//
'/N'//
trim(timetag)//
'00_SALINITY_HYCOM_24h.dat'
411 open(unit=8,file=file_out, form=
'UNFORMATTED')
415 deallocate(iv_sm, m_sm, m_osm, m_out, a_in, a_out)
416 deallocate(i_out, j_out, x_out, y_out)
419 write(*,*)
'NETCDF=N'//
trim(timetag)//
'00_SALINITY_HYCOM_24h.nc'
420 write(*,*)
'HDF5 =N'//
trim(timetag)//
'00_SALINITY_HYCOM_24h.h5'
421 write(*,*)
'BINARY=N'//
trim(timetag)//
'00_SALINITY_HYCOM_24h.dat'
426 & a_out,idm_out,jdm_out,
427 & m_in, m_out,i_out,j_out,x_out,y_out)
430 integer idm_in, jdm_in,
432 integer m_out(idm_out,jdm_out),
433 & m_in(idm_in,jdm_in),
434 & i_out(idm_out,jdm_out),
435 & j_out(idm_out,jdm_out)
436 real a_in( idm_in, jdm_in ),
437 & a_out(idm_out,jdm_out),
438 & x_out(idm_out,jdm_out),
439 & y_out(idm_out,jdm_out)
443 integer i,ii,ip,j,jj,jp
444 integer ki,kj,iii,jjj
449 data s / 1.0, 2.0, 1.0,
452 real,
parameter :: spval=2.0**100
458 if (m_out(ii,jj).eq.1)
then
463 if (i.ne.idm_in)
then
478 if (jjj>jdm_in) jjj=jdm_in
481 if (iii==0) iii=idm_in
482 if (iii>idm_in) iii=1
483 if (m_in(iii,jjj).eq.1)
then
484 sa = sa + s(ki,kj)*a_in(iii,jjj)
493 a_out( ii,jj) = sa/ss
498 a_out(ii,jj) = (1.0-sx)*(1.0-sy)*a_in(i, j ) +
499 & (1.0-sx)* sy *a_in(i, jp) +
500 & sx *(1.0-sy)*a_in(ip,j ) +
501 & sx * sy *a_in(ip,jp)
516 print *,
"Output ocean point:", count
520 subroutine landfill(a,mask,m,n, iv,if,il,jf,jl)
523 integer m,n,mask(m,n), iv(n,2),if,il,jf,jl
531 integer,
allocatable :: mm(:,:,:)
533 integer i,ii,ip0,ip1,ipass,j,jj,ki,kj,nleft,nup
541 data lfirst / .true. /
545 data s /1.0, 1.5, 2.0, 1.5, 1.0,
546 & 1.5, 2.0, 3.0, 2.0, 1.5,
547 & 2.0, 3.0, 4.0, 3.0, 2.0,
548 & 1.5, 2.0, 3.0, 2.0, 1.5,
549 & 1.0, 1.5, 2.0, 1.5, 1.0 /
553 allocate( mm(0:m+1,0:n+1,0:1) )
557 mm( : , : ,1) = mm(:,:,0)
565 &
'landfill - m,n,if,il,jf,jl =',m,n,
if,il,jf,jl
573 do i= iv(j,1),iv(j,2)
574 if (mm(i,j,ip0).eq.2)
then
581 if ((ii>0) .and. (ii.le.m) .and. (jj>0)
582 & .and. (jj.le.n))
then
583 if (mm(ii,jj,ip0).eq.1)
then
584 sa = sa + s(ki,kj)*a(ii,jj)
613 write(6,
'(a,i4,a,i6,a,i6,a)')
614 &
'landfill: pass',ipass,
616 &
' points, with',nleft,
' still to fill'
622 mm(if:il,jf:jl,ip0) = mm(if:il,jf:jl,ip1)
629 write(6,
'(/a,i6,a/a/)')
630 &
'error in landfill - ',
631 & nleft,
' "mask==2" values are not fillable',
632 &
'probably a mismatch between input and output land masks'
652 subroutine psmooth(a,mask,amn,amx,m,n)
655 integer m,n,mask(m,n)
656 real a(m,n),amn(m,n),amx(m,n)
660 integer,
allocatable :: mm(:,:)
661 real,
allocatable :: aa(:,:)
663 integer i,ii,j,jj,ki,kj
668 data s / 1.0, 2.0, 1.0,
672 rss = 1.0/sum(s(:,:))
681 allocate( mm(0:m+1,0:n+1) )
690 if (mm(i,j).eq.1)
then
696 if (mm(ii,jj).eq.1)
then
697 sa = sa + s(ki,kj)*aa(ii,jj)
699 sa = sa + s(ki,kj)*aa(i ,j )
703 a(i,j) =
max( amn(i,j),
704 &
min( amx(i,j), sa*rss ) )
717 print *,
"NetCDF return error ", status