#open the template BC file
fname='BCON_v53_1804_run5_regrid_20180331_HUADON_3k'nc1=netCDF4.Dataset(fname,'r+')V1=[list(filter(lambdax:nc1.variables[x].ndim==j,[iforiinnc1.variables]))forjin[1,2,3,4]]nt1,nlay1,nbnd1=nc1.variables[V1[2][1]].shapeDATES=[jul2dt([i,j])fori,jinzip(nc1['TFLAG'][:,0,0],nc1['TFLAG'][:,0,1])]idate={DATES[i]:iforiinrange(nt1)}SDATE=[jul2dt([i,0])foriinset(nc1['TFLAG'][:,0,0])]SDATE.sort()ymds=[i.strftime("%Y%m%d")foriinSDATE]pnyc1=Proj(proj='lcc',datum='NAD83',lat_1=nc1.P_ALP,lat_2=nc1.P_BET,lat_0=nc1.YCENT,lon_0=nc1.XCENT,x_0=0,y_0=0.0)x1d1=[nc1.XORIG+i*nc1.XCELLforiinrange(-1,nc1.NCOLS+1)]y1d1=[nc1.YORIG+j*nc1.YCELLforjinrange(-1,nc1.NROWS+1)]
依序讀取母網格之模擬結果
由於網格甚多,CCTM_ACONC檔案甚大(210G per file),採一一讀取方式,而不使用ncrcat連結成單一大檔。
#read the d1 CCTM_ACONC files (K40)
lay32_40={i:iforiinrange(25)}lay32_40.update({25+(i-26)//2:iforiinrange(26,40,2)})root='/u01/cmaqruns/2018base/data/output_CCTM_v53_gcc_1804_run5/CCTM_ACONC_v53_gcc_1804_run5_'tail='_CWBWRF_15k_11.nc'fnames=[root+ymd+tailforymdinymds]# turning points among nbnd1 sequence
N0=0N1=N0+nc1.NCOLS+1N2=N1+nc1.NROWS+1N3=N2+nc1.NCOLS+1N4=N3+nc1.NROWS+1forfnameinfnames[:1]:nc=netCDF4.Dataset(fname,'r')
在母網格中定位子網格的4個角落
定位只需執行一次
由於子、母網格的中心點不同,有位移(dx,dy),需先將其計算出來。
母網格座標系統平移到子網格上
以bisect在母網格x1d,y1d序列中,找到子網格4個角落的位置
# interpolation indexing
iffname==fnames[0]:V=[list(filter(lambdax:nc.variables[x].ndim==j,[iforiinnc.variables]))forjin[1,2,3,4]]nt,nlay,nrow,ncol=(nc.variables[V[3][0]].shape[i]foriinrange(4))# traslation of map centers
dx,dy=pnyc1(nc.XCENT,nc.YCENT,inverse=False)# parent grid coordinates in new system
x1d=[nc.XORIG+i*nc.XCELL+dxforiinrange(ncol)]y1d=[nc.YORIG+j*nc.YCELL+dyforjinrange(nrow)]# locate the corner grids
i0,i1=bisect(x1d,x1d1[0])-1,bisect(x1d,x1d1[-1])j0,j1=bisect(y1d,y1d1[0])-1,bisect(y1d,y1d1[-1])
CubicSpline進行內插
子網格的邊界軌跡始於其西南角落,向東、向北、向西、再向南逆時針方向行進,讀取母網格數據。
向西、向南的順序與x1d1、y1d1相反,此處使用np.flip翻轉內插結果,填入子網格檔案。
forttinrange(nt):t=idate(jul2dt(nc['TFLAG'][tt,0,:]))forkinrange(nlay1):kk=lay32_40[k]# set(V[3])==set(V1[2]) ,checked before running
forvinV[3]:# boundary tract begin with South-West corner(j0,i0), and go around the domain in counter-clock wise direction
nc1[v][t,k,N0:N1]=CubicSpline(x1d[i0:i1+1],nc[v][tt,kk,j0,i0:i1+1])(x1d1[:-1])nc1[v][t,k,N1:N2]=CubicSpline(y1d[j0:j1+1],nc[v][tt,kk,j0:j1+1,i1])(y1d1[:-1])nc1[v][t,k,N2:N3]=np.flip(CubicSpline(x1d[i0:i1+1],nc[v][tt,kk,j1,i0:i1+1])(x1d1[:-1]),axis=0)nc1[v][t,k,N3:N4]=np.flip(CubicSpline(y1d[j0:j1+1],nc[v][tt,kk,j0:j1+1,i0])(y1d1[:-1]),axis=0)print(t)nc.close()nc1.close()