PROGRAM ARPSTRAJC ,46
!
!##################################################################
!##################################################################
!###### ######
!###### PROGRAM ARPSTRAJC ######
!###### ######
!###### Developed by ######
!###### Center for Analysis and Prediction of Storms ######
!###### University of Oklahoma ######
!###### ######
!##################################################################
!##################################################################
!
!-----------------------------------------------------------------------
!
! PURPOSE:
!
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! (4/08/2004)
!
! MODIFICATION HISTORY:
!
! 9/28/2005
! Modified to handle terrain-following grid. 3D zp is defined.
! Removed used dignositc codes and arrays
!
!-----------------------------------------------------------------------
!
! Variable Declarations:
!
!-----------------------------------------------------------------------
!
IMPLICIT NONE
REAL, allocatable :: x(:),y(:),z(:)
REAL, allocatable :: xs (:), ys (:) ! x,y coord for scalar points
REAL, allocatable :: u(:,:,:)
REAL, allocatable :: v(:,:,:)
REAL, allocatable :: w(:,:,:)
REAL, allocatable :: zp(:,:,:)
! REAL, allocatable :: ptbar(:),pbar(:),rhobar(:),qvbar(:)
INTEGER (KIND=selected_int_kind(4)), ALLOCATABLE :: itmp(:,:,:) ! Temporary array
INTEGER :: nx,ny,nz,nzsoil ! Grid dimensions.
INTEGER :: nstyps ! Maximum number of soil types.
INTEGER :: hinfmt,nhisfile_max,nhisfile,lengbf
PARAMETER (nhisfile_max=2000)
CHARACTER (LEN=256) :: grdbasfn,hisfile(nhisfile_max)
INTEGER :: hdmpinopt, nf
CHARACTER (LEN=256) :: hdmpftrailer
CHARACTER (LEN=256) :: hdmpfheader
REAL :: tintv_dmpin, tbgn_dmpin, tend_dmpin
NAMELIST /history_data/ hinfmt, nhisfile, grdbasfn, hisfile, &
hdmpinopt,hdmpfheader,hdmpftrailer, &
tintv_dmpin, tbgn_dmpin, tend_dmpin
INTEGER, PARAMETER :: nmax_trajcs=1000, nmax_times=20
REAL :: xtrajc0(nmax_trajcs,nmax_times), &
ytrajc0(nmax_trajcs,nmax_times), &
ztrajc0(nmax_trajcs,nmax_times),ttrajc0
INTEGER :: ntrajc0,ntrajcs, npoints
!
! initrajc = 1 ! specified locations
! = 2 ! circle of radius radius and athimuthal angle increments of theta_inc
! = 3 ! square of radius radius and athimuthal angle increments of theta_inc
! = 4 ! read in from trajectory data file
!
CHARACTER(LEN=256) :: trajc_fn_in(nmax_times)
REAL :: radius,xctr,yctr,zctr(100),theta_inc
INTEGER :: initrajc,nzctr, ntimes
CHARACTER (LEN=256) :: trajcfn_header
REAL :: reftime(nmax_times)
NAMELIST /trajectories/ trajcfn_header,ntimes,reftime, initrajc, ntrajcs, &
xtrajc0,ytrajc0,ztrajc0,ttrajc0,ntrajc0, &
radius,xctr,yctr,zctr,nzctr,theta_inc, trajc_fn_in
REAL, allocatable :: xtrajc(:,:,:),ytrajc(:,:,:),ztrajc(:,:,:),ttrajc(:)
REAL, allocatable :: utrajc(:,:,:),vtrajc(:,:,:),wtrajc(:,:,:)
! REAL, allocatable :: xweight(:,:),yweight(:,:),zweight(:,:)
! INTEGER, allocatable :: itrajc(:,:),jtrajc(:,:),ktrajc(:,:)
INTEGER :: istatus, cur_level
REAL :: tinc
!
!-----------------------------------------------------------------------
! Include files:
!-----------------------------------------------------------------------
!
INCLUDE 'globcst.inc'
INCLUDE 'grid.inc'
INTEGER :: i,j,k,ireturn
REAL :: time, time1, time2, amin, amax, degree, degree2radian, theta
LOGICAL :: iexist
REAL :: u1_changed, utem,vtem,wtem, factor
INTEGER :: nfile
REAL :: ttrajc0_in
INTEGER :: ntrajcs_in, ntrajcs_each_j
CHARACTER (LEN=80) :: timsnd1,timsnd2,timsnd0,timsnd3
INTEGER :: tmstrln1,tmstrln2,tmstrln0, nunit(nmax_times),ltrajc_fn,istat,tmstrln3
INTEGER :: kl, notinteg, nunit1(nmax_times)
CHARACTER (LEN=256) :: trajc_fn
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
!
! Beginning of executable code...
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
!
WRITE(6,'(/9(/5x,a)/)') &
'###############################################################', &
'###############################################################', &
'### ###', &
'### Welcome to ARPSTRAJC ###', &
'### ###', &
'###############################################################', &
'###############################################################'
!
!-----------------------------------------------------------------------
! Get the names of the input data files.
!-----------------------------------------------------------------------
!
READ(5,history_data,ERR=100)
WRITE(6,'(a,i3)') 'Input hdmpinopt=', hdmpinopt
WRITE(6,'(a,i3)') 'Input hinfmt =', hinfmt
WRITE(6,'(a,i3)') 'Input nhisfile =', nhisfile
IF( hinfmt /= 3 ) then
Print*,'Only HDF format (3) is supported.'
STOP
ENDIF
WRITE(6,'(a)')'Namelist history_data was successfully read.'
IF( hdmpinopt == 1 ) THEN
CALL gthinfns
(hdmpfheader,hdmpftrailer,hinfmt, &
tintv_dmpin, tbgn_dmpin, tend_dmpin, &
grdbasfn,hisfile,nhisfile)
END IF
IF( nhisfile > nhisfile_max ) THEN
WRITE(6,'(/a,a,I5,/a/)') &
'The number of history files to be processed', &
' exceeded the maximum number ',nhisfile_max, &
'Please increase the size of array hisfile.'
END IF
lengbf =len_trim( grdbasfn )
WRITE(6,'(/a,a)')'The grid base-state file name is ', &
grdbasfn(1:lengbf)
DO nfile=1,nhisfile
WRITE(6,'(a,i3,a,a)') &
'History file No.',nfile,' is ',trim(hisfile(nfile))
END DO
initrajc = 1
reftime = 0.0
trajcfn_header = ' '
nzctr = 1
ntimes = 1
ttrajc0=0.0
ntrajc0=1
xtrajc0(:,:)=0.0
ytrajc0(:,:)=0.0
ztrajc0(:,:)=0.0
READ(5,trajectories, END=100)
WRITE(6,'(/a,a/)') 'NAMELIST block trajectories successfully read.'
trajc_fn_in(:)='default_trajecotry_filename'
write(6,*) 'Print out namelist block trajectories parameters read in.'
write(6,trajectories)
IF( ntimes > nmax_times ) then
print*,'ntimes in input file exceeded max allowed value of ', nmax_times
STOP
ENDIF
IF( initrajc == 1 .and. ntrajcs > nmax_trajcs ) then
Print*,'ntrajcs larger than maximum allowed. Increase nmax_trajcs in program to ',ntrajcs
STOP
endif
degree2radian = 4.0*atan(1.0)/180.0
IF( initrajc == 2 ) then ! circle
ntrajcs_each_j = nint( 360.0/theta_inc ) + 1
ntrajcs = nzctr * ntrajcs_each_j
IF( ntrajcs > nmax_trajcs ) then
Print*,'ntrajcs larger than maximum allowed. Increase nmax_trajcs in program to ',ntrajcs
STOP
endif
print*,'ntrajcs,nzctr,initrajc=',ntrajcs,nzctr,initrajc
do k=1,ntimes
do j=1,nzctr
xtrajc0((j-1)*(ntrajcs_each_j)+1,k)= xctr
ytrajc0((j-1)*(ntrajcs_each_j)+1,k)= yctr
ztrajc0((j-1)*(ntrajcs_each_j)+1,k)= zctr(j)
do i=1,ntrajcs
theta = (i-1)*theta_inc * degree2radian
xtrajc0((j-1)*(ntrajcs_each_j)+(i+1),k)= xctr+radius*sin( theta )
ytrajc0((j-1)*(ntrajcs_each_j)+(i+1),k)= yctr+radius*cos( theta )
ztrajc0((j-1)*(ntrajcs_each_j)+(i+1),k)= zctr(j)
enddo
enddo
enddo
endif
IF( initrajc == 3 ) then ! box
ntrajcs = nint( 360.0/theta_inc )
IF( ntrajcs > nmax_trajcs ) then
Print*,'ntrajcs larger than maximum allowed. Increase nmax_trajcs in program to ',ntrajcs
STOP
endif
do k=1,ntimes
do i=1,ntrajcs
degree = (i-1)*theta_inc
theta = degree * degree2radian
if( degree <= 45.0 ) then
xtrajc0(i,k)= xctr+radius
ytrajc0(i,k)= yctr+radius*tan( theta )
elseif( degree <= 135.0 ) then
xtrajc0(i,k)= xctr+radius*cos( theta )
ytrajc0(i,k)= yctr+radius
elseif( degree <= 225.0 ) then
xtrajc0(i,k)= xctr-radius
ytrajc0(i,k)= yctr+radius*tan( theta )
elseif( degree <= 315.0 ) then
xtrajc0(i,k)= xctr+radius*cos( theta )
ytrajc0(i,k)= yctr-radius
else
xtrajc0(i,k)= xctr+radius
ytrajc0(i,k)= yctr+radius*tan( theta )
endif
ztrajc0(i,k)=zctr(1)
enddo
enddo
endif
print*,'I am here. initrajc, ntrajcs=', initrajc, ntrajcs
IF( initrajc == 4 ) then ! read from file
DO k=1,ntimes
CALL getunit
(nunit(k))
OPEN(UNIT=nunit(k),FILE=trim(trajc_fn_in(k)),STATUS='old',FORM='formatted')
READ(nunit(k),*)
READ(nunit(k),*)
READ(nunit(k),*)
READ(nunit(k),*)
READ(nunit(k),*)
READ(nunit(k),*)
READ(nunit(k),'(4e17.6)') ttrajc0_in
READ(nunit(k),'(i10)') ntrajcs_in
print*,'ntrajcs_in=', ntrajcs_in
IF( ntrajcs_in /= ntrajcs ) then
print*,'ntrajcs read in .ne. ntrajcs in program. Value in data used.'
ntrajcs = ntrajcs_in
ENDIF
READ(nunit(k),'(6e17.6)') ((xtrajc0(i,k),ytrajc0(i,k),ztrajc0(i,k)),i=1,ntrajcs)
CLOSE(nunit(k))
call retunit(nunit(k))
ENDDO
ENDIF
DO k=1,ntimes
print*,'I am here now. ntrajcs=',ntrajcs,' No. of times=', k
write(6,'(6e17.6)') ((xtrajc0(i,k),ytrajc0(i,k),ztrajc0(i,k)),i=1,ntrajcs)
ENDDO
IF( hdmpinopt == 1 ) THEN
CALL gthinfns
(hdmpfheader,hdmpftrailer,hinfmt, &
tintv_dmpin, tbgn_dmpin, tend_dmpin, &
grdbasfn,hisfile,nhisfile)
END IF
IF( nhisfile > nhisfile_max ) THEN
WRITE(6,'(/a,a,I5,/a/)') &
'The number of history files to be processed', &
' exceeded the maximum number ',nhisfile_max, &
'Please increase the size of array hisfile.'
END IF
lengbf =len_trim( grdbasfn )
WRITE(6,'(/a,a)')'The grid base-state file name is ', &
grdbasfn(1:lengbf)
DO nf=1,nhisfile
WRITE(6,'(a,i3,a,a)') &
'History file No.',nf,' is ',trim(hisfile(nf))
END DO
npoints = nhisfile
lengbf = len_trim(grdbasfn)
WRITE(6,'(/a,a)')' The grid/base name is ', trim(grdbasfn)
CALL get_dims_from_data
(hinfmt,grdbasfn(1:lengbf), &
nx,ny,nz,nzsoil,nstyps, ireturn)
Print*,'nx,ny,nz of input data were ', nx,ny,nz
allocate(x(nx ),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:x")
x = 0.0
allocate(y(ny ),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:y")
y = 0.0
allocate(z(nz ),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:z")
z = 0.0
allocate(xs(nx),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:xs")
xs = 0.0
allocate(ys(ny),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:ys")
ys = 0.0
allocate(u(nx,ny,nz),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:u")
u=0.0
allocate(v(nx,ny,nz),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:v")
v=0.0
allocate(w(nx,ny,nz),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:w")
w=0.0
allocate(zp(nx,ny,nz),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:zp")
zp=0.0
allocate(itmp(nx,ny,nz),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:itmp")
itmp=0
print*,'npoints,ntrajcs=', npoints,ntrajcs
allocate(xtrajc(npoints,ntrajcs,ntimes),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:xtrajc")
allocate(ytrajc(npoints,ntrajcs,ntimes),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:ytrajc")
allocate(ztrajc(npoints,ntrajcs,ntimes),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:ztrajc")
allocate(utrajc(npoints,ntrajcs,ntimes),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:utrajc")
allocate(vtrajc(npoints,ntrajcs,ntimes),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:vtrajc")
allocate(wtrajc(npoints,ntrajcs,ntimes),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:wtrajc")
! allocate(xweight(npoints,ntrajcs),stat=istatus)
! CALL check_alloc_status(istatus, "arpstrajc:xweight")
! allocate(yweight(npoints,ntrajcs),stat=istatus)
! CALL check_alloc_status(istatus, "arpstrajc:yweight")
! allocate(zweight(npoints,ntrajcs),stat=istatus)
! CALL check_alloc_status(istatus, "arpstrajc:zweight")
! allocate(itrajc(npoints,ntrajcs),stat=istatus)
! CALL check_alloc_status(istatus, "arpstrajc:itrajc")
! allocate(jtrajc(npoints,ntrajcs),stat=istatus)
! CALL check_alloc_status(istatus, "arpstrajc:jtrajc")
! allocate(ktrajc(npoints,ntrajcs),stat=istatus)
! CALL check_alloc_status(istatus, "arpstrajc:ktrajc")
allocate(ttrajc(npoints),stat=istatus)
CALL check_alloc_status
(istatus, "arpstrajc:ttrajc")
if( hdmpinopt == 1 ) then ! determine ntrajc0 from ttrajc0
! ttrajc0 is known
ntrajc0 = nint( (ttrajc0 - tbgn_dmpin)/tintv_dmpin ) + 1
else
! ntrajc0 is known from namelist input
! Get ttrajc0 from NO. ntrajc0 history data
endif
print*,'ntrajc0 =', ntrajc0
DO k=1,ntimes
DO j=1,ntrajcs
xtrajc(ntrajc0,j,k)=xtrajc0(j,k)
ytrajc(ntrajc0,j,k)=ytrajc0(j,k)
ztrajc(ntrajc0,j,k)=ztrajc0(j,k)
ENDDO
ENDDO
CALL get_gridinfo_from_hdf
(grdbasfn(1:lengbf),nx,ny,nz,x,y,z,ireturn)
Print*,'x,y,z of input data read in.'
print*,'x(1 )=',x(1)
print*,'x(nx)=',x(nx)
print*,'y(1 )=',y(1)
print*,'y(ny)=',y(ny)
dx = x(2) - x(1)
dy = y(2) - y(1)
IF( ireturn /= 0 ) THEN
PRINT*,'Problem occured when trying to get dimensions from data.'
PRINT*,'Program stopped.'
STOP
END IF
WRITE(6,'(4(a,i5))') 'nx =',nx,', ny=',ny,', nz=',nz ,'nzsoil=',nzsoil
!-----------------------------------------------------------------------
! Find start and end times for trajectories from data
! for hdmpinopt =2.
!-----------------------------------------------------------------------
IF( hdmpinopt == 1 ) then
ttrajc(1) = tbgn_dmpin
ttrajc(npoints) = tend_dmpin
ELSE
nfile = nhisfile
CALL dtareadwind
(nx,ny,nz,x,y,z,zp, trim(grdbasfn),trim(hisfile(nfile)), &
time,u,v,w, itmp)
ttrajc(npoints) = time
nfile = 1
print*,'calling dtareadwind to read file ', trim(hisfile(nfile))
CALL dtareadwind
(nx,ny,nz,x,y,z,zp, trim(grdbasfn),trim(hisfile(nfile)), &
time,u,v,w, itmp)
ttrajc(1) = time
ENDIF
!-----------------------------------------------------------------------
! Read history data at the starting (reference) time of trajectories.
!-----------------------------------------------------------------------
nfile = ntrajc0
WRITE(6,'(/a,a,a)') ' Data set ', trim(hisfile(nfile)),' to be read.'
CALL dtareadwind
(nx,ny,nz,x,y,z,zp, trim(grdbasfn),trim(hisfile(nfile)), &
time,u,v,w, itmp)
ttrajc0 = time
time1 = time
ttrajc(nfile)=time
print*,'ntrajc0, ttrajc0=', ntrajc0, ttrajc0
print*,'At time=', ttrajc0, 'xtrajc(1),ytrajc(1),ztrajc(1) =', &
xtrajc(nfile,1,1),ytrajc(nfile,1,1),ztrajc(nfile,1,1)
print*,'Data at Time =', time, ' read.'
write(0,*) 'before a3dmax0u'
CALL a3dmax0
(u,1,nx,1,nx,1,ny,1,ny-1,1,nz,1,nz-1, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'umin = ', amin,', umax =',amax
write(0,*) 'before a3dmax0v'
CALL a3dmax0
(v,1,nx,1,nx-1,1,ny,1,ny,1,nz,1,nz-1, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'vmin = ', amin,', vmax =',amax
write(0,*) 'before a3dmax0w'
CALL a3dmax0
(w,1,nx,1,nx-1,1,ny,1,ny-1,1,nz,1,nz, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'wmin = ', amin,', wmax =',amax
print*,'Data at Time =', time, ' read.'
write(6,*) 'here'
DO i=1,nx-1
xs(i) = 0.5*(x(i)+x(i+1))
ENDDO
DO j=1,ny-1
ys(j) = 0.5*(y(j)+y(j+1))
ENDDO
write(6,*) 'ntimes = ',ntimes
!-----------------------------------------------------------------------
! Open trajectory data file and write header information
!-----------------------------------------------------------------------
IF( trajcfn_header == ' ' ) trajcfn_header = runname
DO k=1,ntimes
CALL cvttsnd
( ttrajc0 , timsnd0, tmstrln0 )
CALL cvttsnd
( ttrajc(1) , timsnd1, tmstrln1 )
CALL cvttsnd
( ttrajc(npoints), timsnd2, tmstrln2 )
CALL cvttsnd
( reftime(k), timsnd3, tmstrln3 )
trajc_fn = trim(trajcfn_header)//'.trajc_'//trim(timsnd1)//'-'//trim(timsnd2)//'_'//trim(timsnd3)
CALL getunit
( nunit(k))
ltrajc_fn = len_trim(trajc_fn)
CALL fnversn
( trajc_fn, ltrajc_fn )
OPEN(UNIT=nunit(k),FILE=trim(trajc_fn),STATUS='unknown', &
FORM='formatted',IOSTAT= istat )
CALL getunit
( nunit1(k))
OPEN(UNIT=nunit1(k),FILE=trim(trajc_fn)//'.backward',STATUS='unknown', &
FORM='formatted',IOSTAT= istat )
WRITE(nunit(k),'(a)') trim(trajcfn_header)
WRITE(nunit(k),'(6e17.6)') x(2),x(nx-1),y(2),y(ny-1),z(2),z(nz-1)
WRITE(nunit(k),'(3e17.6)') dx, dy, z(2)-z(1)
WRITE(nunit(k),'(3e17.6)') ttrajc(1),ttrajc0,ttrajc(npoints)
WRITE(nunit(k),'(i10)') npoints
WRITE(nunit(k),'(i10)') ntrajcs
WRITE(nunit1(k),'(a)') trim(trajcfn_header)
WRITE(nunit1(k),'(6e17.6)') x(2),x(nx-1),y(2),y(ny-1),z(2),z(nz-1)
WRITE(nunit1(k),'(3e17.6)') dx, dy, z(2)-z(1)
WRITE(nunit1(k),'(3e17.6)') ttrajc(1),ttrajc0,ttrajc(npoints)
WRITE(nunit1(k),'(i10)') npoints
WRITE(nunit1(k),'(i10)') ntrajcs
notinteg = 1
tinc = 1.0 ! should not be used because notinteg = 1
cur_level = ntrajc0
CALL calc_trajc
(nx,ny,nz,xs,ys,zp,u,v,w,tinc,cur_level, &
xtrajc(1,1,k),ytrajc(1,1,k),ztrajc(1,1,k), &
utrajc(1,1,k),vtrajc(1,1,k),wtrajc(1,1,k), &
! itrajc,jtrajc,ktrajc,xweight,yweight,zweight, &
npoints,ntrajcs, notinteg)
j=ntrajc0
write(nunit1(k),'(4e17.6)') ttrajc(j)
write(nunit1(k),'(i10)') ntrajcs
write(nunit1(k),'(6e17.6)') ((xtrajc(j,i,k),ytrajc(j,i,k),ztrajc(j,i,k)),i=1,ntrajcs)
ENDDO
!-----------------------------------------------------------------------
! Calculate backward trajectories.
!-----------------------------------------------------------------------
time1 = ttrajc(ntrajc0)
DO nfile = ntrajc0-1,1,-1
WRITE(6,'(/a,a,a)') ' Data set ', trim(hisfile(nfile)),' to be read.'
CALL dtareadwind
(nx,ny,nz,x,y,z,zp, trim(grdbasfn),trim(hisfile(nfile)), &
time,u,v,w, itmp)
time2 = time
ttrajc(nfile)=time
print*,'Data at Time =', time, ' read.'
CALL a3dmax0
(u,1,nx,1,nx,1,ny,1,ny-1,1,nz,1,nz-1, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'umin = ', amin,', umax =',amax
CALL a3dmax0
(v,1,nx,1,nx-1,1,ny,1,ny,1,nz,1,nz-1, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'vmin = ', amin,', vmax =',amax
CALL a3dmax0
(w,1,nx,1,nx-1,1,ny,1,ny-1,1,nz,1,nz, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'wmin = ', amin,', wmax =',amax
write(0,*) 'here'
!-----------------------------------------------------------------------
! Calculate trajectories
!-----------------------------------------------------------------------
write(0,*) 'calling calc_trajc ',time2, time1
tinc = time2-time1
cur_level = nfile+1
notinteg = 0
DO k=1,ntimes
write(0,*) 'calling calc_trajc'
CALL calc_trajc
(nx,ny,nz,xs,ys,zp,u,v,w,tinc,cur_level, &
xtrajc(1,1,k),ytrajc(1,1,k),ztrajc(1,1,k), &
utrajc(1,1,k),vtrajc(1,1,k),wtrajc(1,1,k), &
! itrajc,jtrajc,ktrajc,xweight,yweight,zweight, &
npoints,ntrajcs, notinteg)
print*,'At time=', time2, 'xtrajc(1),ytrajc(1) =', xtrajc(nfile,1,1),ytrajc(nfile,1,1)
time1 = time2
j = nfile
write(nunit1(k),'(4e17.6)') ttrajc(j)
write(nunit1(k),'(i10)') ntrajcs
write(nunit1(k),'(6e17.6)') ((xtrajc(j,i,k),ytrajc(j,i,k),ztrajc(j,i,k)),i=1,ntrajcs)
ENDDO
ENDDO
DO k=1,ntimes
!-----------------------------------------------------------------------
! Write out the backward trajectory points into the combined trajectory file
!-----------------------------------------------------------------------
do j=1,ntrajc0
write(nunit(k),'(4e17.6)') ttrajc(j)
write(nunit(k),'(i10)') ntrajcs
write(nunit(k),'(6e17.6)') ((xtrajc(j,i,k),ytrajc(j,i,k),ztrajc(j,i,k)),i=1,ntrajcs)
enddo
CLOSE(nunit1(k),status='delete') ! No need for this file anymore
CALL retunit(nunit1(k))
ENDDO
!-----------------------------------------------------------------------
! Calculate forward trajectories
! First re-read data at starting (reference) time if necessary.
!-----------------------------------------------------------------------
time1 = ttrajc(ntrajc0)
DO nfile = ntrajc0+1,npoints,+1
WRITE(6,'(/a,a,a)') ' Data set ', trim(hisfile(nfile)),' to be read.'
CALL dtareadwind
(nx,ny,nz,x,y,z,zp, trim(grdbasfn),trim(hisfile(nfile)), &
time,u,v,w, itmp)
time2 = time
ttrajc(nfile)=time
print*,'Data at Time =', time, ' read.'
CALL a3dmax0
(u,1,nx,1,nx,1,ny,1,ny-1,1,nz,1,nz-1, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'umin = ', amin,', umax =',amax
CALL a3dmax0
(v,1,nx,1,nx-1,1,ny,1,ny,1,nz,1,nz-1, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'vmin = ', amin,', vmax =',amax
CALL a3dmax0
(w,1,nx,1,nx-1,1,ny,1,ny-1,1,nz,1,nz, amax,amin)
WRITE(6,'(1x,2(a,e13.6))') 'wmin = ', amin,', wmax =',amax
write(0,*) 'here'
!-----------------------------------------------------------------------
! Calculate trajectories
!-----------------------------------------------------------------------
write(0,*) 'calling calc_trajc ',time2, time1
tinc = time2-time1
cur_level = nfile-1
notinteg = 0
! print*,'cur_level =', cur_level
! print*,'xtrajc(cur_level,:) =', xtrajc(cur_level,1), xtrajc(cur_level,2)
DO k=1,ntimes
write(0,*) 'calling calc_trajc'
CALL calc_trajc
(nx,ny,nz,xs,ys,zp,u,v,w,tinc,cur_level, &
xtrajc(1,1,k),ytrajc(1,1,k),ztrajc(1,1,k), &
utrajc(1,1,k),vtrajc(1,1,k),wtrajc(1,1,k), &
! itrajc,jtrajc,ktrajc,xweight,yweight,zweight, &
npoints,ntrajcs, notinteg)
time1 = time2
print*,'At time=', time2, 'xtrajc(1),ytrajc(1),ztrajc(1) =', &
xtrajc(nfile,1,k),ytrajc(nfile,1,k),ztrajc(nfile,1,k)
!-----------------------------------------------------------------------
! Write out the forward trajectory points
!-----------------------------------------------------------------------
j = nfile
write(nunit(k),'(4e17.6)') ttrajc(j)
write(nunit(k),'(i10)') ntrajcs
write(nunit(k),'(6e17.6)') ((xtrajc(j,i,k),ytrajc(j,i,k),ztrajc(j,i,k)),i=1,ntrajcs)
ENDDO
ENDDO
!-----------------------------------------------------------------------
! Close the trajectory file
!-----------------------------------------------------------------------
DO k=1,ntimes
CLOSE(UNIT=nunit(k))
CALL retunit( nunit(k))
ENDDO
STOP
100 WRITE(6,'(a)') 'Error reading NAMELIST file. Program ARPSTRAJC stopped.'
STOP
END PROGRAM ARPSTRAJC
!
!##################################################################
!##################################################################
!###### ######
!###### SUBROUTINE DTAREADWIND ######
!###### ######
!###### Developed by ######
!###### Center for Analysis and Prediction of Storms ######
!###### University of Oklahoma ######
!###### ######
!##################################################################
!##################################################################
!
SUBROUTINE dtareadwind(nx,ny,nz,x,y,z,zp, grdbasfn,datafn, time,u,v,w, itmp) 5,16
!
!-----------------------------------------------------------------------
! Variable Declarations.
!-----------------------------------------------------------------------
!
IMPLICIT NONE
INTEGER :: nx,ny,nz ! Number of grid points in 3 directions
INTEGER :: hinfmt ! The format of the history data dump
CHARACTER(LEN=*) :: grdbasfn ! Name of the grid/base state array file
CHARACTER(LEN=*) :: datafn ! Name of the other time dependent data file
REAL :: x(nx),y(ny),z(nz)
REAL :: time
REAL :: u(nx,ny,nz)
REAL :: v(nx,ny,nz)
REAL :: w(nx,ny,nz)
REAL :: zp(nx,ny,nz)
INTEGER (KIND=selected_int_kind(4)) :: itmp(nx,ny,nz) ! Temporary array
INTEGER :: grdread,iread
SAVE grdread
INTEGER :: istat
INTEGER :: ireturn ! Return status indicator
INTEGER :: grdbas ! Wether this is a grid/base state
! array dump
INTEGER :: i,j,k
LOGICAL :: fexist
INTEGER :: is
!
!-----------------------------------------------------------------------
!
! Include files:
!
!-----------------------------------------------------------------------
!
INCLUDE 'indtflg.inc'
INCLUDE 'globcst.inc'
INCLUDE 'grid.inc' ! Grid & map parameters.
INCLUDE 'mp.inc' ! mpi parameters.
INCLUDE 'exbc.inc'
INCLUDE 'phycst.inc'
DATA grdread /0/
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
!
! Beginning of executable code...
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
!
ireturn = 0
hinfmt = 3
!
!-----------------------------------------------------------------------
!
! Open and read grid and base state data file depending on the
! values of parameters grdin and basin, which are read in from the
! time dependent data set. If grdin or basin is zero, the grid and
! base state arrays have to be read in from a separate file.
!
!-----------------------------------------------------------------------
!
Print*,'In dtareadwind, grdbasfn =', trim(grdbasfn)
Print*,'In dtareadwind, datafn =', trim(datafn)
IF( grdread == 0 ) THEN
! print*,'grdread inside if block=', grdread
grdbas = 1
INQUIRE(FILE=grdbasfn, EXIST = fexist )
IF( fexist ) GO TO 200
INQUIRE(FILE=grdbasfn//'.Z', EXIST = fexist )
IF( fexist ) THEN
CALL uncmprs
( grdbasfn//'.Z' )
GO TO 200
END IF
INQUIRE(FILE=grdbasfn//'.gz', EXIST = fexist )
IF( fexist ) THEN
CALL uncmprs
( grdbasfn//'.gz' )
GO TO 200
END IF
WRITE(6,'(/1x,a,/1x,a/)') &
'File '//grdbasfn// &
' or its compressed version not found.', &
'Program stopped in DTAREADWIND location 1.'
CALL arpsstop
('arpsstop called from dtareadwind during base state read',1)
200 CONTINUE
!
!-----------------------------------------------------------------------
! Read grid and base state fields.
!-----------------------------------------------------------------------
!
CALL hdfreadwind
(nx,ny,nz,x,y,z,zp,grdbas,trim(grdbasfn), &
time,u,v,w, itmp)
grdread = 1
END IF
!
!-----------------------------------------------------------------------
! Read data fields.
!-----------------------------------------------------------------------
!
grdbas = 0
INQUIRE(FILE=trim(datafn), EXIST = fexist )
IF( fexist ) GO TO 100
INQUIRE(FILE=trim(datafn)//'.Z', EXIST = fexist )
IF( fexist ) THEN
CALL uncmprs
( trim(datafn)//'.Z' )
GO TO 100
END IF
INQUIRE(FILE=trim(datafn)//'.gz', EXIST = fexist )
IF( fexist ) THEN
CALL uncmprs
( trim(datafn)//'.gz' )
GO TO 100
END IF
WRITE(6,'(/1x,a,/1x,a/)') &
'File '//trim(datafn) &
//' or its compressed version not found.', &
'Program stopped in DTAREADWIND location 2.'
CALL arpsstop
('arpsstop called from dtareadwind during base read-2',1)
100 CONTINUE
CALL hdfreadwind
(nx,ny,nz,x,y,z,zp,grdbas,trim(datafn), &
time,u,v,w, itmp)
RETURN
END SUBROUTINE dtareadwind
!##################################################################
!##################################################################
!###### ######
!###### SUBROUTINE HDFREAD ######
!###### ######
!###### Developed by ######
!###### Center for Analysis and Prediction of Storms ######
!###### University of Oklahoma ######
!###### ######
!##################################################################
!##################################################################
SUBROUTINE hdfreadwind(nx,ny,nz,x,y,z,zp,grdbas,filename, & 4,122
time,u,v,w, itmp)
!-----------------------------------------------------------------------
! PURPOSE:
! Read in history data in the NCSA HDF4 format.
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! 2000/04/15
!
! MODIFICATION HISTORY:
!-----------------------------------------------------------------------
!
! INPUT :
!
! nx Number of grid points in the x-direction (east/west)
! ny Number of grid points in the y-direction (north/south)
! nz Number of grid points in the vertical
!
! grdbas Data read flag.
! =1, only grid and base state arrays will be read
! =0, all arrays will be read based on data
! parameter setting.
! filename Character variable nhming the input HDF file
!-----------------------------------------------------------------------
! Variable Declarations.
!-----------------------------------------------------------------------
IMPLICIT NONE
INTEGER :: nx,ny,nz
INTEGER :: grdbas
CHARACTER (LEN=*) :: filename
REAL :: x (nx) ! x coord.
REAL :: y (ny) ! y coord.
REAL :: z (nz) ! z coord.
REAL :: time
REAL :: u(nx,ny,nz)
REAL :: v(nx,ny,nz)
REAL :: w(nx,ny,nz)
REAL :: zp(nx,ny,nz)
INTEGER (KIND=selected_int_kind(4)) :: itmp(nx,ny,nz) ! Temporary array
REAL :: hmax(nz), hmin(nz) ! Temporary array
INTEGER :: ireturn
!-----------------------------------------------------------------------
! Parameters describing routine that wrote the gridded data
!-----------------------------------------------------------------------
!
! 06/28/2002 Zuwen He
!
! fmtver??: to label each data a version.
! intver??: an integer to allow faster comparison than fmtver??,
! which are strings.
!
! Verion 5.00: significant change in soil variables since version 4.10.
!
!-----------------------------------------------------------------------
CHARACTER (LEN=40) :: fmtver410,fmtver500
INTEGER :: intver,intver410,intver500
PARAMETER (fmtver410='004.10 HDF4 Coded Data',intver410=410)
PARAMETER (fmtver500='005.00 HDF4 Coded Data',intver500=500)
CHARACTER (LEN=40) :: fmtverin
CHARACTER (LEN=10) :: tmunit
!-----------------------------------------------------------------------
! Misc. local variables
!-----------------------------------------------------------------------
INTEGER :: lchanl
PARAMETER (lchanl=6) ! Channel number for formatted printing.
INTEGER :: i,j,k,is
INTEGER :: nxin,nyin,nzin
INTEGER :: bgrdin,bbasin,bvarin,bicein,btrbin,btkein
INTEGER :: istat, sd_id
INTEGER :: varflg, istatus
!-----------------------------------------------------------------------
!
! Include files:
!
!-----------------------------------------------------------------------
INCLUDE 'globcst.inc'
INCLUDE 'grid.inc' ! Grid parameters
INCLUDE 'indtflg.inc'
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
! Beginning of executable code...
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
WRITE(*,*) 'HDFREAD: Reading HDF file: ', trim(filename)
!-----------------------------------------------------------------------
! Open file for reading
!-----------------------------------------------------------------------
CALL hdfopen
(filename,1,sd_id)
IF (sd_id < 0) THEN
WRITE (6,*) "HDFREAD: ERROR opening ", trim(filename)," for reading."
GO TO 110
END IF
fmtverin = fmtver500
WRITE(6,'(/1x,a,a/)') 'Incoming data format, fmtverin=',fmtverin
CALL hdfrdc
(sd_id,40,"runname",runname,istat)
CALL hdfrdi
(sd_id,"nocmnt",nocmnt,istat)
IF( nocmnt > 0 ) THEN
CALL hdfrdc
(sd_id,80*nocmnt,"cmnt",cmnt,istat)
END IF
WRITE(6,'(//'' THE NAME OF THIS RUN IS: '',A//)') trim(runname)
WRITE (6,*) "Comments:"
IF( nocmnt > 0 ) THEN
DO i=1,nocmnt
WRITE(6,'(1x,a)') cmnt(i)
END DO
END IF
WRITE (6,*) " "
CALL hdfrdc
(sd_id,10,"tmunit",tmunit,istat)
CALL hdfrdr
(sd_id,"time",time,istat)
!-----------------------------------------------------------------------
! Get dimensions of data in binary file and check against
! the dimensions passed to HDFREAD
!-----------------------------------------------------------------------
CALL hdfrdi
(sd_id,"nx",nxin,istat)
CALL hdfrdi
(sd_id,"ny",nyin,istat)
CALL hdfrdi
(sd_id,"nz",nzin,istat)
IF ( nxin /= nx .OR. nyin /= ny .OR. nzin /= nz ) THEN
WRITE(6,'(1x,a)') ' Dimensions in HDFREAD inconsistent with data.'
WRITE(6,'(1x,a,3I15)') ' Read were: ', nxin, nyin, nzin
WRITE(6,'(1x,a,3I15)') ' Expected: ', nx, ny, nz
WRITE(6,'(1x,a)') ' Program aborted in HDFREAD.'
CALL arpsstop
('arpsstop called from HDFREAD due to nxin...',1)
END IF
!-----------------------------------------------------------------------
! Read in x,y and z at grid cell centers (scalar points).
!-----------------------------------------------------------------------
IF( grdin == 1 .OR. grdbas == 1 ) THEN
CALL hdfrd1d
(sd_id,"x",nx,x,istat)
IF (istat /= 0) GO TO 110
CALL hdfrd1d
(sd_id,"y",ny,y,istat)
IF (istat /= 0) GO TO 110
CALL hdfrd1d
(sd_id,"z",nz,z,istat)
IF (istat /= 0) GO TO 110
END IF ! grdin
!-----------------------------------------------------------------------
! Read in flags for different data groups
!-----------------------------------------------------------------------
IF ( grdbas == 1 ) THEN ! Read grid and base state arrays
WRITE(lchanl,'(1x,a,f8.1,a,f8.3,a/)') &
'To read grid and base state data at time ', time, &
' secs = ',(time/60.),' mins.'
CALL hdfrdi
(sd_id,"grdflg",bgrdin,istat)
CALL hdfrdi
(sd_id,"basflg",bbasin,istat)
CALL hdfrdi
(sd_id,"varflg",bvarin,istat)
CALL hdfrdi
(sd_id,"mstflg",mstin,istat)
CALL hdfrdi
(sd_id,"iceflg",bicein,istat)
CALL hdfrdi
(sd_id,"trbflg",btrbin,istat)
CALL hdfrdi
(sd_id,"landflg",landin,istat)
CALL hdfrdi
(sd_id,"totflg",totin,istat)
CALL hdfrdi
(sd_id,"tkeflg",btkein,istat)
ELSE ! Normal data reading
WRITE(lchanl,'(1x,a,f8.1,a,f8.3,a/)')'To read data for time:', &
time,' secs = ',(time/60.),' mins.'
CALL hdfrdi
(sd_id,"grdflg",grdin,istat)
CALL hdfrdi
(sd_id,"basflg",basin,istat)
CALL hdfrdi
(sd_id,"varflg",varin,istat)
CALL hdfrdi
(sd_id,"mstflg",mstin,istat)
CALL hdfrdi
(sd_id,"iceflg",icein,istat)
CALL hdfrdi
(sd_id,"trbflg",trbin,istat)
CALL hdfrdi
(sd_id,"sfcflg",sfcin,istat)
CALL hdfrdi
(sd_id,"rainflg",rainin,istat)
CALL hdfrdi
(sd_id,"totflg",totin,istat)
CALL hdfrdi
(sd_id,"tkeflg",tkein,istat)
print*,'done reading parameters'
END IF
CALL hdfrdi
(sd_id,"prcflg",prcin,istat)
CALL hdfrdi
(sd_id,"radflg",radin,istat)
CALL hdfrdi
(sd_id,"flxflg",flxin,istat)
CALL hdfrdi
(sd_id,"snowflg",snowin,istat)
CALL hdfrdi
(sd_id,"month",month,istat)
CALL hdfrdi
(sd_id,"day",day,istat)
CALL hdfrdi
(sd_id,"year",year,istat)
CALL hdfrdi
(sd_id,"hour",hour,istat)
CALL hdfrdi
(sd_id,"minute",minute,istat)
CALL hdfrdi
(sd_id,"second",second,istat)
CALL hdfrdr
(sd_id,"umove",umove,istat)
CALL hdfrdr
(sd_id,"vmove",vmove,istat)
CALL hdfrdr
(sd_id,"xgrdorg",xgrdorg,istat)
CALL hdfrdr
(sd_id,"ygrdorg",ygrdorg,istat)
CALL hdfrdi
(sd_id,"mapproj",mapproj,istat)
CALL hdfrdr
(sd_id,"trulat1",trulat1,istat)
CALL hdfrdr
(sd_id,"trulat2",trulat2,istat)
CALL hdfrdr
(sd_id,"trulon",trulon,istat)
CALL hdfrdr
(sd_id,"sclfct",sclfct,istat)
CALL hdfrdr
(sd_id,"tstop",tstop,istat)
CALL hdfrdr
(sd_id,"thisdmp",thisdmp,istat)
CALL hdfrdr
(sd_id,"latitud",latitud,istat)
CALL hdfrdr
(sd_id,"ctrlat",ctrlat,istat)
CALL hdfrdr
(sd_id,"ctrlon",ctrlon,istat)
IF( grdin == 1 .OR. grdbas == 1 ) THEN
CALL hdfrd3d
(sd_id,"zp",nx,ny,nz,zp,istat,itmp,hmax,hmin)
IF (istat /= 0) GO TO 110
ENDIF
!-----------------------------------------------------------------------
! Read in base state fields
!-----------------------------------------------------------------------
! Print*,'start doing 3d arrays'
IF( (basin == 1 .OR. grdbas == 1) .and. hdmpfmt /= 0) THEN
! CALL hdfrd3d(sd_id,"ubar",nx,ny,nz,ubar,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! CALL hdfrd3d(sd_id,"vbar",nx,ny,nz,vbar,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! CALL hdfrd3d(sd_id,"ptbar",nx,ny,nz,ptbar,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! CALL hdfrd3d(sd_id,"pbar",nx,ny,nz,pbar,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! IF( mstin == 1 ) THEN
! CALL hdfrd3d(sd_id,"qvbar",nx,ny,nz,qvbar,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! ELSE
! qvbar= 0.0
! END IF
ENDIF
landout = 0 ! skipping landout for know
IF( grdbas == 1 ) GO TO 930
IF( varin == 1 ) then
!-----------------------------------------------------------------------
! Read in total values of variables from history dump
!-----------------------------------------------------------------------
CALL hdfrd3d
(sd_id,"u",nx,ny,nz,u,istat,itmp,hmax,hmin)
IF (istat /= 0) GO TO 110
CALL hdfrd3d
(sd_id,"v",nx,ny,nz,v,istat,itmp,hmax,hmin)
IF (istat /= 0) GO TO 110
CALL hdfrd3d
(sd_id,"w",nx,ny,nz,w,istat,itmp,hmax,hmin)
IF (istat /= 0) GO TO 110
! CALL hdfrd3d(sd_id,"pt",nx,ny,nz,pt,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! CALL hdfrd3d(sd_id,"p",nx,ny,nz,p,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! IF( mstin == 1 ) THEN
! CALL hdfrd3d(sd_id,"qv",nx,ny,nz,qv,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
!
! CALL hdfrd3d(sd_id,"qc",nx,ny,nz,qc,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
!
! CALL hdfrd3d(sd_id,"qr",nx,ny,nz,qr,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! IF( icein == 1 ) THEN
! CALL hdfrd3d(sd_id,"qi",nx,ny,nz,qi,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
!
! CALL hdfrd3d(sd_id,"qs",nx,ny,nz,qs,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
!
! CALL hdfrd3d(sd_id,"qh",nx,ny,nz,qh,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! END IF
! END IF
END IF
! IF( tkein == 1 ) THEN
! CALL hdfrd3d(sd_id,"tke",nx,ny,nz,tke,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! END IF
! IF( trbin == 1 ) THEN
! CALL hdfrd3d(sd_id,"kmh",nx,ny,nz,kmh,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! CALL hdfrd3d(sd_id,"kmv",nx,ny,nz,,istat,itmp,hmax,hmin)
! IF (istat /= 0) GO TO 110
! END IF
!
! Surface arrays skipped
!
!-----------------------------------------------------------------------
!
! Friendly exit message
!
!-----------------------------------------------------------------------
930 CONTINUE
WRITE(6,'(/a,F8.1,a/)') &
' Data at time=', time/60,' (min) were successfully read.'
ireturn = 0
GO TO 130
!-----------------------------------------------------------------------
!
! Error during read
!
!-----------------------------------------------------------------------
110 CONTINUE
WRITE(6,'(/a/)') ' Error reading data in HDFREAD'
STOP
ireturn=1
130 CONTINUE
CALL hdfclose
(sd_id,istat)
IF (ireturn == 0) THEN
IF (istat == 0) THEN
WRITE(6,'(/a/a)') &
"HDFREADWIND: Successfully read ", trim(filename)
ELSE
WRITE(6,'(/a,i3,a/,a)') &
"HDFREADWIND: ERROR (status=", istat, ") closing ", trim(filename)
STOP
END IF
END IF
RETURN
END SUBROUTINE hdfreadwind
!##################################################################
!##################################################################
!###### ######
!###### SUBROUTINE GET_GRIDINFO_FROM_HDF ######
!###### ######
!###### Developed by ######
!###### Center for Analysis and Prediction of Storms ######
!###### University of Oklahoma ######
!###### ######
!##################################################################
!##################################################################
SUBROUTINE get_gridinfo_from_hdf(filename,nx,ny,nz,x,y,z,ireturn) 2,15
!
!-----------------------------------------------------------------------
!
! PURPOSE:
! Read in grid dimensions from base state/grid history data.
!
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! 7/17/2000.
!
! MODIFICATION HISTORY:
!
!-----------------------------------------------------------------------
!
! INPUT :
!
! filename Channel number for binary reading.
!
! OUTPUT:
!
! nx Number of grid points in the x-direction (east/west)
! ny Number of grid points in the y-direction (north/south)
! nz Number of grid points in the vertical
!
!-----------------------------------------------------------------------
IMPLICIT NONE
INTEGER :: stat, sd_id
CHARACTER (LEN=*) :: filename
INTEGER :: nx,ny,nz ! Number of grid points in 3 directions
REAL :: x(nx),y(ny),z(nz)
INTEGER :: ireturn ! Return status indicator
INTEGER istat
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
!
! Beginning of executable code...
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
CALL hdfopen
(filename,1,sd_id)
IF (sd_id < 0) THEN
WRITE (6,*) "get_gridinfo_from_hdf: ERROR opening ", &
trim(filename)," for reading."
GO TO 110
ELSE
WRITE(6,*) 'File ',filename,' openned.'
END IF
! print*,'sd_id, nx =', sd_id, nx
CALL hdfrd1d
(sd_id,"x",nx,x,istat)
! print*,'istat after reading x =', istat
IF (istat /= 0) GO TO 110
CALL hdfrd1d
(sd_id,"y",ny,y,istat)
IF (istat /= 0) GO TO 110
CALL hdfrd1d
(sd_id,"z",nz,z,istat)
IF (istat /= 0) GO TO 110
ireturn = 0
GO TO 130
!-----------------------------------------------------------------------
!
! Error during read
!
!-----------------------------------------------------------------------
110 CONTINUE
WRITE(6,'(/a/)') ' Error reading data in GET_GRIDINFO_FROM_HDF.'
print*,'Program stopped in GET_GRIDINFO_FROM_HDF.'
STOP
ireturn=1
130 CONTINUE
!tmp stat = sfendacc(sd_id) ! is this necessary?
CALL hdfclose
(sd_id,stat)
RETURN
END SUBROUTINE get_gridinfo_from_hdf
SUBROUTINE copyarray(arrayin,nx,ny,nz, arrayout, nx1,ny1,nz1, & 32
nxbgn,nxend,nybgn,nyend,nzbgn,nzend)
INTEGER :: nx,ny,nz, nx1,ny1,nz1,nxbgn,nxend,nybgn,nyend,nzbgn,nzend
REAL :: arrayin(nx,ny,nz)
REAL :: arrayout(nx1,ny1,nz1)
DO k=1,nz1
DO j=1,ny1
DO i=1,nx1
arrayout(i,j,k)=arrayin(nxbgn+i-1,nybgn+j-1,nzbgn+k-1)
ENDDO
ENDDO
ENDDO
return
END SUBROUTINE copyarray
SUBROUTINE intrpx3d(ain,nx,is,ie, ny,js,je, nz,ks,ke, wgtx,ix, & 3
aout,nx1,is1,ie1)
!
!-----------------------------------------------------------------------
!
! PURPOSE:
! Perform interpolation in the first dimension
!
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! 4/1/1999.
!
! MODIFICATION HISTORY:
!
!-----------------------------------------------------------------------
IMPLICIT NONE
INTEGER :: nx,is,ie, ny,js,je, nz,ks,ke
INTEGER :: nx1,is1,ie1
REAL :: ain (nx ,ny,nz)
REAL :: aout(nx1,ny,nz)
REAL :: wgtx(nx1)
INTEGER :: ix(nx1)
INTEGER :: i,j,k
DO k=ks ,ke
DO j=js ,je
DO i=is1,ie1
aout(i,j,k)= wgtx(i) *ain(ix(i) ,j,k) &
+(1.0-wgtx(i))*ain(ix(i)+1,j,k)
END DO
END DO
END DO
RETURN
END SUBROUTINE intrpx3d
SUBROUTINE intrpy3d(ain,nx,is,ie, ny,js,je, nz,ks,ke, wgty,jy, & 3
aout,ny1,js1,je1)
!
!-----------------------------------------------------------------------
!
! PURPOSE:
! Perform interpolation in the second dimension
!
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! 4/1/1999.
!
! MODIFICATION HISTORY:
!
!-----------------------------------------------------------------------
!
IMPLICIT NONE
INTEGER :: nx,is,ie, ny,js,je, nz,ks,ke
INTEGER :: ny1,js1,je1
REAL :: ain (nx,ny ,nz)
REAL :: aout(nx,ny1,nz)
REAL :: wgty(ny1)
INTEGER :: jy(ny1)
INTEGER :: i,j,k
DO k=ks ,ke
DO j=js1,je1
DO i=is ,ie
aout(i,j,k)= wgty(j) *ain(i,jy(j) ,k) &
+(1.0-wgty(j))*ain(i,jy(j)+1,k)
END DO
END DO
END DO
RETURN
END SUBROUTINE intrpy3d
SUBROUTINE intrpxy3d(ain,nx,is,ie, ny,js,je, nz,ks,ke, & 53,8
wgtx,ix,wgty,jy, &
aout,nx1,is1,ie1, ny1,js1,je1, &
temx1yz)
!
!-----------------------------------------------------------------------
!
! PURPOSE:
! Perform interpolation in the first and second dimensions
!
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! 4/1/1999.
!
! MODIFICATION HISTORY:
!
!-----------------------------------------------------------------------
!
IMPLICIT NONE
INTEGER :: nx,is,ie, ny,js,je, nz,ks,ke
INTEGER :: nx1,is1,ie1, ny1,js1,je1
REAL :: ain (nx ,ny ,nz)
REAL :: aout(nx1,ny1,ks:ke)
REAL :: wgtx(nx1),wgty(ny1)
INTEGER :: ix(nx1),jy(ny1)
INTEGER :: k
REAL :: temx1yz(nx1,ny)
DO k=ks,ke
CALL intrpx3d
(ain(1,1,k),nx,is,ie, ny,js,je, 1,1,1, &
wgtx,ix,temx1yz,nx1,is1,ie1)
CALL intrpy3d
(temx1yz,nx1,is1,ie1, ny,js,je, 1,1,1, &
wgty,jy,aout(1,1,k),ny1,js1,je1)
ENDDO
CALL edgfill
(aout,1,nx1,is1,ie1,1,ny1,js1,je1,ks,ke,ks,ke)
RETURN
END SUBROUTINE intrpxy3d
SUBROUTINE calc_trajc(nx,ny,nz,xs,ys,zp,u,v,w,tinc,clevel, & 3
xtrajc,ytrajc,ztrajc,utrajc,vtrajc,wtrajc, &
! itrajc,jtrajc,ktrajc,xweight,yweight,zweight, &
ntrajc_points,ntrajcs, notinteg)
!
!-----------------------------------------------------------------------
! PURPOSE:
!-----------------------------------------------------------------------
!
! AUTHOR: Ming Xue
! (4/08/2004)
!
! MODIFICATION HISTORY:
!
!-----------------------------------------------------------------------
! Variable Declarations:
!-----------------------------------------------------------------------
!
IMPLICIT NONE
INTEGER :: nx,ny,nz
REAL :: xs(nx),ys(ny),zp(nx,ny,nz)
REAL :: u(nx,ny,nz)
REAL :: v(nx,ny,nz)
REAL :: w(nx,ny,nz)
INTEGER :: ntrajc_points,ntrajcs
REAL :: xtrajc(ntrajc_points,ntrajcs),ytrajc(ntrajc_points,ntrajcs)
REAL :: ztrajc(ntrajc_points,ntrajcs)
REAL :: utrajc(ntrajc_points,ntrajcs),vtrajc(ntrajc_points,ntrajcs),wtrajc(ntrajc_points,ntrajcs)
! REAL :: xweight(ntrajc_points,ntrajcs),yweight(ntrajc_points,ntrajcs),zweight(ntrajc_points,ntrajcs)
! INTEGER :: itrajc(ntrajc_points,ntrajcs),jtrajc(ntrajc_points,ntrajcs),ktrajc(ntrajc_points,ntrajcs)
REAL :: tinc
INTEGER :: clevel, flevel,get_ktrajc
INTEGER :: niteration,niteration_max,ntrajc,level_inc
REAL :: dx, dy, utrajc1,vtrajc1,wtrajc1
REAL :: uy1z1,uy2z1,uy1z2,uy2z2,vy1z1,vy2z1,vy1z2,vy2z2,wy1z1,wy2z1,wy1z2,wy2z2
REAL :: uz1,uz2,vz1,vz2,wz1,wz2
REAL :: missing_value
INTEGER :: notinteg ! for the first time step where xtrajc,ytrajc,ztrajc
! are known and no time integration of trajectory is performed.
INTEGER :: niterat,itrajc1,jtrajc1,ktrajc1
REAL :: xweight1,yweight1,zweight1
REAL :: zs1d(nz),zy1(nz),zy2(nz) ! automatic work array
INTEGER :: i,j,k, vlevel
!
!-----------------------------------------------------------------------
! Include files:
!-----------------------------------------------------------------------
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
!
! Begin of executable code
!
!@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
write(0,*) 'entering calc_trajc'
dx = xs(2)-xs(1)
dy = ys(2)-ys(1)
IF( tinc == 0 ) then
Print*,'tinc cannot be equal 0, job stopped in calc_trajc.'
STOP
ENDIF
! print*,'mark 1'
IF( tinc > 0 ) level_inc = 1
IF( tinc < 0 ) level_inc = -1
flevel = clevel + level_inc
if( notinteg == 1 ) flevel = clevel
niteration_max = 7
IF( notinteg == 1 ) THEN
niterat = 1
ELSE
niterat = niteration_max
ENDIF
! print*,'ntrajc_points,ntrajcs=', ntrajc_points,ntrajcs
! print*,'mark 2, flevel =', flevel, clevel, level_inc
xtrajc(flevel,:) = xtrajc(clevel,:)
ytrajc(flevel,:) = ytrajc(clevel,:)
ztrajc(flevel,:) = ztrajc(clevel,:)
! print*,'xtrajc(clevel,:), xtrajc(flevel,:)=', xtrajc(clevel,:), xtrajc(flevel,:)
! print*,'ytrajc(clevel,:), ytrajc(flevel,:)=', ytrajc(clevel,:), ytrajc(flevel,:)
! print*,'ztrajc(clevel,:), ztrajc(flevel,:)=', ztrajc(clevel,:), ztrajc(flevel,:)
! print*,' I am here'
missing_value = -99999.0
write(0,*) 'inside calc_trajc ',ntrajcs
DO ntrajc = 1,ntrajcs
write(0,*) 'ntrajc = ',ntrajc
IF( xtrajc(clevel,ntrajc) == missing_value .or. &
ytrajc(clevel,ntrajc) == missing_value .or. &
ztrajc(clevel,ntrajc) == missing_value ) cycle
DO niteration = 1, niterat
write(0,*) 'niteration = ',niteration, niterat
IF( niteration == 1 .and. notinteg /= 1 ) THEN
utrajc1 = utrajc(clevel,ntrajc)
vtrajc1 = vtrajc(clevel,ntrajc)
wtrajc1 = wtrajc(clevel,ntrajc)
ELSE
itrajc1 = MAX(1, MIN(nx-2, INT((xtrajc(flevel,ntrajc)-xs(1))/dx)+1 ))
jtrajc1 = MAX(1, MIN(ny-2, INT((ytrajc(flevel,ntrajc)-ys(1))/dy)+1 ))
write(0,*) 'xtrajc = ',flevel,xtrajc(flevel,ntrajc)
xweight1 = (xtrajc(flevel,ntrajc)-xs(itrajc1))/dx
yweight1 = (ytrajc(flevel,ntrajc)-ys(jtrajc1))/dy
! DTD test initial trajectory height
IF(notinteg == 1) THEN
print*,'Before: itrajc1,jtrajc1,ztrajc,zp(k=1)',itrajc1,jtrajc1,ztrajc(clevel,ntrajc),zp(itrajc1,jtrajc1,1)
! adjust initial trajectory height to be consistent with zp array, which is in ASL (user input should
! be interpreted as being AGL)
ztrajc(clevel,ntrajc)=ztrajc(clevel,ntrajc)+zp(itrajc1,jtrajc1,1)
print*,'After: itrajc1,jtrajc1,ztrajc,zp(k=1)',itrajc1,jtrajc1,ztrajc(clevel,ntrajc),zp(itrajc1,jtrajc1,1)
END IF
DO k=1,nz-1
zy1(k) = (1.0-xweight1)*(zp(itrajc1 ,jtrajc1 ,k)+zp(itrajc1 ,jtrajc1 ,k+1))*0.5 &
+xweight1 *(zp(itrajc1+1,jtrajc1 ,k)+zp(itrajc1+1,jtrajc1 ,k+1))*0.5
zy2(k) = (1.0-xweight1)*(zp(itrajc1 ,jtrajc1+1,k)+zp(itrajc1 ,jtrajc1+1,k+1))*0.5 &
+xweight1 *(zp(itrajc1+1,jtrajc1+1,k)+zp(itrajc1+1,jtrajc1+1,k+1))*0.5
zs1d(k) = ( 1.0-yweight1 )*zy1(k) + yweight1*zy2(k)
END DO
write(0,*) ' here 2'
ktrajc1 = get_ktrajc(ztrajc(flevel,ntrajc),zs1d,nz-1)
! print*,'niteration =', niteration
! print*,'xtrajc, ytrajc, ztrajc=', xtrajc(flevel,ntrajc),ytrajc(flevel,ntrajc),ztrajc(flevel,ntrajc)
! print*,'itrajc,jtrajc ,ktrajc =',itrajc1,jtrajc1 ,ktrajc1
uy1z1 = (1.0-xweight1)*(u(itrajc1 ,jtrajc1 ,ktrajc1 )+u(itrajc1+1,jtrajc1 ,ktrajc1 ))*0.5 &
+xweight1*(u(itrajc1+1,jtrajc1 ,ktrajc1 )+u(itrajc1+2,jtrajc1 ,ktrajc1 ))*0.5
uy2z1 = (1.0-xweight1)*(u(itrajc1 ,jtrajc1+1,ktrajc1 )+u(itrajc1+1,jtrajc1+1,ktrajc1 ))*0.5 &
+xweight1 *(u(itrajc1+1,jtrajc1+1,ktrajc1 )+u(itrajc1+2,jtrajc1+1,ktrajc1 ))*0.5
uy1z2 = (1.0-xweight1)*(u(itrajc1 ,jtrajc1 ,ktrajc1+1)+u(itrajc1+1,jtrajc1 ,ktrajc1+1))*0.5 &
+xweight1* (u(itrajc1+1,jtrajc1 ,ktrajc1+1)+u(itrajc1+2,jtrajc1 ,ktrajc1+1))*0.5
uy2z2 = (1.0-xweight1)*(u(itrajc1 ,jtrajc1+1,ktrajc1+1)+u(itrajc1+1,jtrajc1+1,ktrajc1+1))*0.5 &
+xweight1* (u(itrajc1+1,jtrajc1+1,ktrajc1+1)+u(itrajc1+2,jtrajc1+1,ktrajc1+1))*0.5
vy1z1 = (1.0-xweight1)*(v(itrajc1 ,jtrajc1 ,ktrajc1 )+v(itrajc1 ,jtrajc1+1,ktrajc1 ))*0.5 &
+xweight1* (v(itrajc1+1,jtrajc1 ,ktrajc1 )+v(itrajc1+1,jtrajc1+1,ktrajc1 ))*0.5
vy2z1 = (1.0-xweight1)*(v(itrajc1 ,jtrajc1+1,ktrajc1 )+v(itrajc1 ,jtrajc1+2,ktrajc1 ))*0.5 &
+xweight1* (v(itrajc1+1,jtrajc1+1,ktrajc1 )+v(itrajc1+1,jtrajc1+2,ktrajc1 ))*0.5
vy1z2 = (1.0-xweight1)*(v(itrajc1 ,jtrajc1 ,ktrajc1+1)+v(itrajc1 ,jtrajc1+1,ktrajc1+1))*0.5 &
+xweight1* (v(itrajc1+1,jtrajc1 ,ktrajc1+1)+v(itrajc1+1,jtrajc1+1,ktrajc1+1))*0.5
vy2z2 = (1.0-xweight1)*(v(itrajc1 ,jtrajc1+1,ktrajc1+1)+v(itrajc1 ,jtrajc1+2,ktrajc1+1))*0.5 &
+xweight1* (v(itrajc1+1,jtrajc1+1,ktrajc1+1)+v(itrajc1+1,jtrajc1+2,ktrajc1+1))*0.5
wy1z1 = (1.0-xweight1)*(w(itrajc1 ,jtrajc1 ,ktrajc1 )+w(itrajc1 ,jtrajc1 ,ktrajc1+1))*0.5 &
+xweight1* (w(itrajc1+1,jtrajc1 ,ktrajc1 )+w(itrajc1+1,jtrajc1 ,ktrajc1+1))*0.5
wy2z1 = (1.0-xweight1)*(w(itrajc1 ,jtrajc1+1,ktrajc1 )+w(itrajc1 ,jtrajc1+1,ktrajc1+1))*0.5 &
+xweight1* (w(itrajc1+1,jtrajc1+1,ktrajc1 )+w(itrajc1+1,jtrajc1+1,ktrajc1+1))*0.5
wy1z2 = (1.0-xweight1)*(w(itrajc1 ,jtrajc1 ,ktrajc1+1)+w(itrajc1 ,jtrajc1 ,ktrajc1+2))*0.5 &
+xweight1* (w(itrajc1+1,jtrajc1 ,ktrajc1+1)+w(itrajc1+1,jtrajc1 ,ktrajc1+2))*0.5
wy2z2 = (1.0-xweight1)*(w(itrajc1 ,jtrajc1+1,ktrajc1+1)+w(itrajc1 ,jtrajc1+1,ktrajc1+2))*0.5 &
+xweight1* (w(itrajc1+1,jtrajc1+1,ktrajc1+1)+w(itrajc1+1,jtrajc1+1,ktrajc1+2))*0.5
write(0,*) 'wylz2,wy2z2',wy1z2,wy2z2, xweight1
write(0,*) 'here 3 ',itrajc1, jtrajc1, ktrajc1, w(itrajc1 ,jtrajc1 ,ktrajc1+1)
uz1 = ( 1.0-yweight1 )*uy1z1 + yweight1*uy2z1
uz2 = ( 1.0-yweight1 )*uy1z2 + yweight1*uy2z2
vz1 = ( 1.0-yweight1 )*vy1z1 + yweight1*vy2z1
vz2 = ( 1.0-yweight1 )*vy1z2 + yweight1*vy2z2
wz1 = ( 1.0-yweight1 )*wy1z1 + yweight1*wy2z1
wz2 = ( 1.0-yweight1 )*wy1z2 + yweight1*wy2z2
write(0,*) 'here 4 ',ktrajc1,zs1d(ktrajc1+1), zs1d(ktrajc1)
zweight1 = (ztrajc(flevel,ntrajc)-zs1d(ktrajc1))/(zs1d(ktrajc1+1)-zs1d(ktrajc1))
write(0,*) 'here 4.1'
utrajc1 = (1.0-zweight1)*uz1+zweight1*uz2
write(0,*) 'here 4.2'
vtrajc1 = (1.0-zweight1)*vz1+zweight1*vz2
write(0,*) 'here 4.3', wz1, wz2
wtrajc1 = (1.0-zweight1)*wz1+zweight1*wz2
write(0,*) 'here 5'
ENDIF
! print*,'xweight,yweight,zweight=', xweight1,yweight1,zweight1
! print*,'tinc =', tinc
write(0,*) 'notinteg = ',notinteg
IF( notinteg /= 1 ) THEN
IF( xtrajc(clevel,ntrajc) .ne. missing_value ) then
xtrajc(flevel,ntrajc) = xtrajc(clevel,ntrajc) + tinc * 0.5*(utrajc(clevel,ntrajc)+utrajc1)
ELSE
xtrajc(flevel,ntrajc) = missing_value
ENDIF
IF( ytrajc(clevel,ntrajc) .ne. missing_value ) then
ytrajc(flevel,ntrajc) = ytrajc(clevel,ntrajc) + tinc * 0.5*(vtrajc(clevel,ntrajc)+vtrajc1)
ELSE
ytrajc(flevel,ntrajc) = missing_value
ENDIF
ztrajc(flevel,ntrajc) = ztrajc(clevel,ntrajc) + tinc * 0.5*(wtrajc(clevel,ntrajc)+wtrajc1)
! print*,'xtrajc, ytrajc, ztrajc=', xtrajc(flevel,ntrajc),ytrajc(flevel,ntrajc),ztrajc(flevel,ntrajc)
ENDIF
! print*,'clevel,flevel,niteration,ntrajc=',clevel,flevel,niteration,ntrajc
! print*,'utrajc0,vtrajc0,wtrajc0=', utrajc(clevel,ntrajc),vtrajc(clevel,ntrajc),wtrajc(clevel,ntrajc)
! print*,'utrajc1,vtrajc1,wtrajc1=', utrajc1,vtrajc1,wtrajc1
! print*,'xtrajc, ytrajc, ztrajc=', xtrajc(flevel,ntrajc),ytrajc(flevel,ntrajc),ztrajc(flevel,ntrajc)
ENDDO ! niteration
write(0,*) 'here 1'
utrajc(flevel,ntrajc) = utrajc1
vtrajc(flevel,ntrajc) = vtrajc1
wtrajc(flevel,ntrajc) = wtrajc1
! xweight(flevel,ntrajc) = xweight1 ! save the calculated weights in array for reuse
! yweight(flevel,ntrajc) = yweight1 ! save the calculated weights in array for reuse
! zweight(flevel,ntrajc) = zweight1 ! save the calculated weights in array for reuse
! itrajc(flevel,ntrajc) = itrajc1 ! save the calculated weights in array for reuse
! jtrajc(flevel,ntrajc) = jtrajc1 ! save the calculated weights in array for reuse
! ktrajc(flevel,ntrajc) = ktrajc1 ! save the calculated weights in array for reuse
IF( notinteg /= 1 ) THEN
ztrajc(flevel,ntrajc) = max(ztrajc(flevel,ntrajc), (zs1d(1)+zs1d(2))*0.5+0.1*(zs1d(2)-zs1d(1)))
ztrajc(flevel,ntrajc) = min(ztrajc(flevel,ntrajc), (zs1d(nz-1)+zs1d(nz-2))*0.5 )
if( xtrajc(flevel,ntrajc) .lt. xs(1) .or. xtrajc(flevel,ntrajc).gt. xs(nx-1) ) then
xtrajc(flevel,ntrajc) = missing_value
endif
if( ytrajc(flevel,ntrajc) .lt. ys(1) .or. ytrajc(flevel,ntrajc).gt. ys(ny-1) ) then
ytrajc(flevel,ntrajc) = missing_value
endif
ENDIF
ENDDO
RETURN
END SUBROUTINE calc_trajc
INTEGER FUNCTION get_ktrajc(z, zs1d, nz)
IMPLICIT NONE
INTEGER :: nz, k
REAL :: z, zs1d(nz)
IF( z < zs1d(1) ) then
get_ktrajc = 1
RETURN
ENDIF
IF( z >= zs1d(nz) ) then
get_ktrajc = nz-1
RETURN
ENDIF
DO k=1,nz-1
IF( z >= zs1d(k) .and. z < zs1d(k+1) ) then
get_ktrajc = k
EXIT
endif
ENDDO
RETURN
END FUNCTION get_ktrajc