Beispiel #1
0
def tide_pred(modfile,lon,lat,time,z=None,conlist=None):
    """
    Performs a tidal prediction at all points in [lon,lat] at times in vector [time]
    
    """
    
    # Read and interpolate the constituents
    u_re, u_im, v_re, v_im, h_re, h_im, omega, conlist = extract_HC(modfile,lon,lat,z=z,conlist=conlist)
    
    # Initialise the output arrays
    sz = lon.shape
    nx = np.prod(sz)
    nt = time.shape[0]
    ncon = omega.shape[0]
    
    h_re = h_re.reshape((ncon,nx))
    h_im = h_im.reshape((ncon,nx))
    u_re = u_re.reshape((ncon,nx))
    u_im = u_im.reshape((ncon,nx))
    v_re = v_re.reshape((ncon,nx))
    v_im = v_im.reshape((ncon,nx))
        
    # Calculate nodal correction to amps and phases
    #baseyear = time[0].year
    #t1992 = othertime.SecondsSince(datetime(baseyear,1,1),basetime=datetime(1992,1,1))/86400.0
    t1992 = othertime.SecondsSince(time[0],basetime=datetime(1992,1,1))/86400.0
    
    pu,pf,v0u = nodal(t1992+48622.0,conlist)
       
    # Calculate the time series
    tsec = othertime.SecondsSince(time,basetime=datetime(1992,1,1)) # Needs to be referenced to 1992

    h=np.zeros((nt,nx))
    u=np.zeros((nt,nx))
    v=np.zeros((nt,nx))
    for nn,om in enumerate(omega):
        for ii in range(0,nx):
            h[:,ii] += pf[nn]*h_re[nn,ii] * np.cos(om*tsec + v0u[nn] + pu[nn]) - \
                pf[nn]*h_im[nn,ii] * np.sin(om*tsec + v0u[nn] + pu[nn])
                
            u[:,ii] += pf[nn]*u_re[nn,ii] * np.cos(om*tsec + v0u[nn] + pu[nn]) - \
                pf[nn]*u_im[nn,ii] * np.sin(om*tsec + v0u[nn] + pu[nn])
                
            v[:,ii] += pf[nn]*v_re[nn,ii] * np.cos(om*tsec + v0u[nn] + pu[nn]) - \
                pf[nn]*v_im[nn,ii] * np.sin(om*tsec + v0u[nn] + pu[nn])
    
    szo = (nt,)+sz
    return h.reshape(szo), u.reshape(szo), v.reshape(szo)
Beispiel #2
0
def extract_phsamp(tidemod, lon, lat, basetime, conlist):
    """
    Extract the phase and amplitude
    """
    u_re, u_im, v_re, v_im, h_re, h_im, omega, conlist =\
        extract_HC(tidemod, lon, lat, conlist = conlist)

    t1992 = othertime.SecondsSince(basetime,basetime=datetime(1992,1,1))/86400.0
    
    pu,pf,v0u = nodal(t1992+48622.0,conlist)

    u_amp = np.abs(u_re + 1j*u_im)
    v_amp = np.abs(v_re + 1j*v_im)
    h_amp = np.abs(h_re + 1j*h_im)
 
    u_phs = np.angle(u_re + 1j*u_im)
    v_phs = np.angle(v_re + 1j*v_im)
    h_phs = np.angle(h_re + 1j*h_im)

    # Apply the corrections
    for ii, cc in enumerate(omega):
        u_amp *= pf[ii]
        v_amp *= pf[ii]
        h_amp *= pf[ii]

        u_phs += (v0u[ii] + pu[ii])
        v_phs += (v0u[ii] + pu[ii])
        h_phs += (v0u[ii] + pu[ii])

    return u_amp, u_phs,\
        v_amp, v_phs,\
        h_amp, h_phs, omega
Beispiel #3
0
def tide_pred_old(modfile,lon,lat,time,z=None,conlist=None):
    """
	
	### UNUSED ###
    Performs a tidal prediction at all points in [lon,lat] at times in vector [time]
    
    """
    
    # Read and interpolate the constituents
    u_re, u_im, v_re, v_im, h_re, h_im, omega, conlist = extract_HC(modfile,lon,lat,z=z,conlist=conlist)
    
    # Initialise the output arrays
    sz = lon.shape
    nx = np.prod(sz)
    nt = time.shape[0]
    ncon = omega.shape[0]
    
    h_re = h_re.reshape((ncon,nx))
    h_im = h_im.reshape((ncon,nx))
    u_re = u_re.reshape((ncon,nx))
    u_im = u_im.reshape((ncon,nx))
    v_re = v_re.reshape((ncon,nx))
    v_im = v_im.reshape((ncon,nx))
    
    # Nodal correction to amps and phases here...
    baseyear = time[0].year
    amp, phase = cart2pol(h_re, h_im)
    amp,phase = nodal_correction(baseyear,conlist, amp, phase)
    h_re, h_im = pol2cart(amp, phase)
    
    amp, phase = cart2pol(u_re, u_im)
    amp, phase = nodal_correction(baseyear,conlist, amp, phase)
    u_re, u_im = pol2cart(amp, phase)
        
    amp, phase = cart2pol(v_re, v_im)
    amp, phase = nodal_correction(baseyear,conlist, amp, phase)
    v_re, v_im = pol2cart(amp, phase)
    
    
    # Calculate the time series
    tsec = othertime.SecondsSince(time,basetime=datetime(baseyear,1,1))
    h=np.zeros((nt,nx))
    u=np.zeros((nt,nx))
    v=np.zeros((nt,nx))
    for nn,om in enumerate(omega):
        for ii in range(0,nx):
            h[:,ii] += h_re[nn,ii] * np.cos(om*tsec) + h_im[nn,ii] * np.sin(om*tsec)
            u[:,ii] += u_re[nn,ii] * np.cos(om*tsec) + u_im[nn,ii] * np.sin(om*tsec)
            v[:,ii] += v_re[nn,ii] * np.cos(om*tsec) + v_im[nn,ii] * np.sin(om*tsec)
    
    szo = (nt,)+sz
    return h.reshape(szo), u.reshape(szo), v.reshape(szo)
Beispiel #4
0
    def __init__(self, x, y, z, timeinfo, tformat='%Y%m%d.%H%M%S', **kwargs):

        metfile.__init__(self, mode='create', **kwargs)

        self.x = x
        self.y = y
        self.z = z
        self.time =\
            otime.TimeVector(timeinfo[0],timeinfo[1],timeinfo[2],timeformat=tformat)
        self.nctime = otime.SecondsSince(self.time)

        #self.varnames = ['Uwind','Vwind','Tair','Pair','RH','rain','cloud']

        # Update all of the metdata objects
        for vv in self.varnames:
            self.updateMetData(self[vv])
Beispiel #5
0
def calc_agebin(binfile, ncfile, polyfile, ntout):
    """
    Calculate the from a binary file and save to netcdf
    """
    # Load the polygon from a shapefile
    xypoly, field = readShpPoly(polyfile)

    # Load the binary file object
    PTM = PtmBin(binfile)

    # Count the number of particles from the first time step
    time, pdata = PTM.read_timestep()
    N = pdata.shape[0]
    tsec = othertime.SecondsSince(PTM.time)
    dt = tsec[1] - tsec[0]

    # Initialize the age particle object
    Age = ParticleAge(xypoly[0], N)

    # Loop through
    outctr = ntout
    ncctr = 0
    for tt in range(PTM.nt - 1):
        # Read the current time step
        time, pdata = PTM.read_timestep(ts=tt)

        # Update the age variable
        Age.update_age(pdata['x'][:, 0], pdata['x'][:, 1], pdata['x'][:, 2],
                       dt)

        # Write to netcdf
        if outctr == ntout:
            Age.write_nc(time, ncctr, ncfile=ncfile)
            ncctr += 1
            outctr = 0
        outctr += 1

    print('Done.')
Beispiel #6
0
def tide_pred_correc(modfile,lon,lat,time,dbfile,ID,z=None,conlist=None):
    """
    Performs a tidal prediction at all points in [lon,lat] at times in vector [time]
    
    Applies an amplitude and phase correction based on a time series
    """
    from timeseries import timeseries, loadDBstation
    
    print('Calculating tidal correction factors from time series...')
    # Load using the timeseries module
    t0 = datetime.strftime(time[0],'%Y%m%d.%H%M%S')
    t1 = datetime.strftime(time[-1],'%Y%m%d.%H%M%S')
    dt = time[1]-time[0]
    
    print(t0, t1, dt.total_seconds())
    timeinfo = (t0,t1,dt.total_seconds())
    TS,meta = loadDBstation(dbfile,ID,'waterlevel',timeinfo=timeinfo,filttype='low',cutoff=2*3600,output_meta=True)
    lonpt=meta['longitude']
    latpt=meta['latitude']
    print(lonpt,latpt)
    
    # Extract the OTIS tide prediction
    u_re, u_im, v_re, v_im, h_re, h_im, omega, conlist = extract_HC(modfile,lonpt,latpt)
    h_amp = np.abs(h_re+1j*h_im)[:,0]
    h_phs = np.angle(h_re+1j*h_im)[:,0]
    
    # Harmonic analysis of observation time series
    amp, phs, frq, frqnames, htide = TS.tidefit(frqnames=conlist)
    TS_harm = timeseries(time,htide)
    residual = TS.y - htide
    
    # Calculate the amp and phase corrections
    dphs = phs - h_phs + np.pi
    damp = amp/h_amp

    # Extract the data along the specified points
    u_re, u_im, v_re, v_im, h_re, h_im, omega, conlist = extract_HC(modfile,lon,lat,z=z,conlist=conlist)
    
    h_amp = np.abs(h_re+1j*h_im)
    h_phs = np.angle(h_re+1j*h_im)
    u_amp = np.abs(u_re+1j*u_im)
    u_phs = np.angle(u_re+1j*u_im)
    v_amp = np.abs(v_re+1j*v_im)
    v_phs = np.angle(v_re+1j*v_im)
        
    # Initialise the output arrays
    sz = lon.shape
    nx = np.prod(sz)
    nt = time.shape[0]

    h=np.zeros((nt,nx))
    u=np.zeros((nt,nx))
    v=np.zeros((nt,nx))
    
    # Rebuild the time series
    #tsec=TS_harm.tsec - TS_harm.tsec[0]
    tsec = othertime.SecondsSince(time,basetime=time[0])
    print(tsec[0])
    for nn,om in enumerate(omega):
        for ii in range(0,nx):
            h[:,ii] += damp[nn]*h_amp[nn,ii] * np.cos(om*tsec - (h_phs[nn,ii] + dphs[nn]))
            u[:,ii] += damp[nn]*u_amp[nn,ii] * np.cos(om*tsec - (u_phs[nn,ii] + dphs[nn]))
            v[:,ii] += damp[nn]*v_amp[nn,ii] * np.cos(om*tsec - (v_phs[nn,ii] + dphs[nn]))
            
    szo = (nt,)+sz
    return h.reshape(szo), u.reshape(szo), v.reshape(szo), residual
Beispiel #7
0
    def writeNC(self, outfile, dv=None):
        """
        Export the results to a netcdf file
        """
        from .suntans_ugrid import ugrid
        from netCDF4 import Dataset

        # Fill in the depths with zero
        #if not self.__dict__.has_key('dv'):
        if dv is None:
            self.dv = np.zeros((self.Nc, ))
        else:
            self.dv = dv
        if 'Nk' not in self.__dict__:
            self.Nk = self.Nkmax * np.ones((self.Nc, ))

        Grid.writeNC(self, outfile)

        # write the time variable
        t = othertime.SecondsSince(self.time)
        self.create_nc_var(outfile, 'time', ugrid['time']['dimensions'],
                           ugrid['time']['attributes'])

        # Create the other variables
        self.create_nc_var(
            outfile, 'eta', ('time', 'Nc'), {
                'long_name': 'Sea surface elevation',
                'units': 'metres',
                'coordinates': 'time yv xv'
            })
        self.create_nc_var(
            outfile, 'uc', ('time', 'Nk', 'Nc'), {
                'long_name': 'Eastward water velocity component',
                'units': 'metre second-1',
                'coordinates': 'time z_r yv xv'
            })
        self.create_nc_var(
            outfile, 'vc', ('time', 'Nk', 'Nc'), {
                'long_name': 'Northward water velocity component',
                'units': 'metre second-1',
                'coordinates': 'time z_r yv xv'
            })
        self.create_nc_var(
            outfile, 'salt', ('time', 'Nk', 'Nc'), {
                'long_name': 'Salinity',
                'units': 'ppt',
                'coordinates': 'time z_r yv xv'
            })
        self.create_nc_var(
            outfile, 'temp', ('time', 'Nk', 'Nc'), {
                'long_name': 'Water temperature',
                'units': 'degrees C',
                'coordinates': 'time z_r yv xv'
            })
        self.create_nc_var(outfile, 'agec', ('time', 'Nk', 'Nc'), {
            'long_name': 'Age concentration',
            'units': ''
        })
        self.create_nc_var(
            outfile, 'agealpha', ('time', 'Nk', 'Nc'), {
                'long_name': 'Age alpha parameter',
                'units': 'seconds',
                'coordinates': 'time z_r yv xv'
            })
        self.create_nc_var(outfile,'agesource',('Nk','Nc'),\
        {'long_name':'Age source grid cell (>0 = source)',\
        'units':'','coordinates':'z_r yv xv'})

        # now write the variables...
        nc = Dataset(outfile, 'a')
        nc.variables['time'][:] = t
        nc.variables['eta'][:] = self.h
        nc.variables['uc'][:] = self.uc
        nc.variables['vc'][:] = self.vc
        nc.variables['salt'][:] = self.S
        nc.variables['temp'][:] = self.T
        nc.variables['agec'][:] = self.agec
        nc.variables['agealpha'][:] = self.agealpha
        nc.variables['agesource'][:] = self.agesource
        nc.close()

        print('Initial condition file written to: %s' % outfile)
Beispiel #8
0
def ProfilePlot(t,y,z,scale=86400,\
        axis=0,color=[0.5,0.5,0.5],xlim=None,units='m/s',scalebar=1.0):
    """
    Plot a series of vertical profiles as a time series
    
    scale - Sets 1 unit = scale (seconds)
    
    See this page on formatting:
        http://matplotlib.org/examples/pylab_examples/date_index_formatter.html
    """
    
    class MyFormatter(Formatter):
        def __init__(self, dates, fmt='%b %d %Y'):
            self.fmt = fmt
            self.dates = dates

        def __call__(self, x, pos=0):
            'Return the label for time x s'
            return datetime.strftime(datetime(1990,1,1)+timedelta(seconds=x),self.fmt)

    tsec = othertime.SecondsSince(t)
    formatter = MyFormatter(tsec)
    
    y = np.swapaxes(y,0,axis)
    
    lines=[]
    line2 =[]
    for ii, tt in enumerate(tsec):
        #xplot = set_scale(y[:,ii],tt)
        xplot = tt + y[:,ii]*scale
        lines.append(np.array((xplot,z)).T)
        line2.append(np.array([[tt,tt],[z[0],z[-1]]]).T)
        
    
    LC1 = collections.LineCollection(lines,colors=color,linewidths=1.5)
    LC2 = collections.LineCollection(line2,colors='k',linestyles='dashed') # Zero axis
    
    ax=plt.gca()
    ax.add_collection(LC1)
    ax.add_collection(LC2)
    ax.set_ylim((z.min(),z.max()))
    ax.xaxis.set_major_formatter(formatter)
    if xlim==None:
        xlim=(tsec[0]-scale/2,tsec[-1]+scale/2)
    else:
        xlim=othertime.SecondsSince(xlim)
    ax.set_xlim(xlim)
    plt.xticks(rotation=17)       

    ###
    # Add a scale bar    
    ###
    
    # Compute the scale bar size in dimensionless units
    if not scalebar==None:
        xscale = scalebar*scale/(xlim[-1]-xlim[0])
        x0 = 0.1
        y0 = 0.8
        dy = 0.02
        ax.add_line(Line2D([x0,x0+xscale],[y0,y0],linewidth=0.5,color='k',transform=ax.transAxes))
        #Little caps
        ax.add_line(Line2D([x0,x0],[y0-dy,y0+dy],linewidth=0.5,color='k',transform=ax.transAxes))
        ax.add_line(Line2D([x0+xscale,x0+xscale],[y0-dy,y0+dy],linewidth=0.5,color='k',transform=ax.transAxes))
        plt.text(x0,y0+0.05,'Scale %3.1f %s'%(scalebar,units),\
            transform=ax.transAxes)

    
    return ax