示例#1
0
    def _init(self, driftersPerOceanModel=1):
        """
        Initiating the ensemble by perturbing the input simulator and attaching drifters
        """
        self.driftersPerOceanModel = np.int32(driftersPerOceanModel)

        for i in range(self.numParticles + 1):
            self.particles[i] = CDKLM16.CDKLM16(self.gpu_ctx, \
                                                self.base_eta, self.base_hu, self.base_hv, \
                                                self.base_H, \
                                                self.nx, self.ny, self.dx, self.dy, self.dt, \
                                                self.g, self.f, self.r, \
                                                boundary_conditions=self.boundaryConditions, \
                                                write_netcdf=False, \
                                                small_scale_perturbation=True, \
                                                small_scale_perturbation_amplitude=self.small_scale_perturbation_amplitude,
                                                small_scale_perturbation_interpolation_factor=self.small_scale_perturbation_interpolation_factor)

            if self.initialization_variance_factor_ocean_field != 0.0:
                self.particles[i].perturbState(
                    q0_scale=self.initialization_variance_factor_ocean_field)

            # Add drifters
            drifters = GPUDrifterCollection.GPUDrifterCollection(
                self.gpu_ctx,
                self.driftersPerOceanModel,
                observation_variance=self.observation_variance,
                boundaryConditions=self.boundaryConditions,
                initialization_cov_drifters=self.initialization_cov_drifters,
                domain_size_x=self.nx * self.dx,
                domain_size_y=self.ny * self.dy)
            self.particles[i].attachDrifters(drifters)
示例#2
0
    def init(self, driftersPerOceanModel=1):
        self.driftersPerOceanModel = driftersPerOceanModel

        # Define mid-points for the different drifters
        # Decompose the domain, so that we spread the drifters as much as possible
        sub_domains_y = np.int(np.round(np.sqrt(self.driftersPerOceanModel)))
        sub_domains_x = np.int(
            np.ceil(1.0 * self.driftersPerOceanModel / sub_domains_y))
        self.midPoints = np.empty((driftersPerOceanModel, 2))
        for sub_y in range(sub_domains_y):
            for sub_x in range(sub_domains_x):
                drifter_id = sub_y * sub_domains_x + sub_x
                if drifter_id >= self.driftersPerOceanModel:
                    break
                self.midPoints[drifter_id,
                               0] = (sub_x +
                                     0.5) * self.nx * self.dx / sub_domains_x
                self.midPoints[drifter_id,
                               1] = (sub_y +
                                     0.5) * self.ny * self.dy / sub_domains_y

        for i in range(self.numParticles + 1):
            self.particles[i] = CDKLM16.CDKLM16(self.gpu_ctx, \
                                                self.base_eta, self.base_hu, self.base_hv, \
                                                self.base_H, \
                                                self.nx, self.ny, self.dx, self.dy, self.dt, \
                                                self.g, self.f, self.r, \
                                                boundary_conditions=self.boundaryConditions, \
                                                write_netcdf=False, \
                                                small_scale_perturbation=True, \
                                                small_scale_perturbation_amplitude=self.small_scale_perturbation_amplitude)

            if self.initialization_variance_factor_ocean_field != 0.0:
                self.particles[i].perturbState(
                    q0_scale=self.initialization_variance_factor_ocean_field)

            drifters = GPUDrifterCollection.GPUDrifterCollection(
                self.gpu_ctx,
                driftersPerOceanModel,
                observation_variance=self.observation_variance,
                boundaryConditions=self.boundaryConditions,
                domain_size_x=self.nx * self.dx,
                domain_size_y=self.ny * self.dy)

            initPos = np.empty((self.driftersPerOceanModel, 2))
            for d in range(self.driftersPerOceanModel):
                initPos[d, :] = np.random.multivariate_normal(
                    self.midPoints[d, :], self.initialization_cov_drifters)
            drifters.setDrifterPositions(initPos)
            #print "drifter particles: ", drifter.getParticlePositions()
            #print "drifter observations: ", drifter.getObservationPosition()
            self.particles[i].attachDrifters(drifters)

        # Put the initial positions into the observation array
        self._addObservation(self.observeTrueDrifters())
示例#3
0
    def __init__(self,
                 gpu_ctx,
                 sim_args,
                 sim_ic,
                 num_particles,
                 drifter_positions=[],
                 observation_variance=0.01**2,
                 initialization_variance_factor_ocean_field=0.0):
        """
        Constructor which creates num_particles slighly different ocean models
        based on the same initial conditions
        """

        self.logger = logging.getLogger(__name__)
        self.gpu_ctx = gpu_ctx
        self.sim_args = sim_args
        self.observation_variance = observation_variance
        self.initialization_variance_factor_ocean_field = initialization_variance_factor_ocean_field

        # Build observation covariance matrix:
        if np.isscalar(self.observation_variance):
            self.observation_cov = np.eye(2) * self.observation_variance
            self.observation_cov_inverse = np.eye(2) * (
                1.0 / self.observation_variance)
        else:
            # Assume that we have a correctly shaped matrix here
            self.observation_cov = self.observation_variance
            self.observation_cov_inverse = np.linalg.inv(self.observation_cov)

        # Generate ensemble members
        self.logger.debug("Creating %d particles (ocean models)",
                          num_particles)
        self.particles = [None] * num_particles
        for i in range(num_particles):
            self.particles[i] = CDKLM16.CDKLM16(self.gpu_ctx, **sim_ic,
                                                **self.sim_args)

            if self.initialization_variance_factor_ocean_field != 0.0:
                self.particles[i].perturbState(
                    q0_scale=self.initialization_variance_factor_ocean_field)

            # Attach drifters if requested
            self.logger.debug("Attaching %d drifters", len(drifter_positions))
            if (len(drifter_positions) > 0):
                drifters = GPUDrifterCollection.GPUDrifterCollection(
                    self.gpu_ctx,
                    len(drifter_positions),
                    observation_variance=self.observation_variance,
                    boundaryConditions=sim_ic['boundary_conditions'],
                    domain_size_x=sim_args['nx'] * sim_args['dx'],
                    domain_size_y=sim_args['ny'] * sim_args['dy'])
                drifters.setDrifterPositions(drifter_positions)
                self.particles[i].attachDrifters(drifters)
示例#4
0
    def init(self, driftersPerOceanModel=1):
        self.windSpeed = 2.0
        self.directions = np.random.rand(self.numParticles + 1) * 360
        self.windX, self.windY = self.XandYfromDirections(self.directions)
        #print "Directions: ", self.directions
        self.driftersPerOceanModel = driftersPerOceanModel

        self.windT = np.zeros((1), dtype=np.float32)

        for i in range(self.numParticles + 1):

            wX = [self.windX[i] * np.ones((2, 2), dtype=np.float32)]
            wY = [self.windY[i] * np.ones((2, 2), dtype=np.float32)]

            wind = WindStress.WindStress(self.windT, wX, wY)
            #print ("Init with wind :", (wX, wY))

            self.particles[i] = CDKLM16.CDKLM16(self.gpu_ctx, \
                                                self.base_eta, self.base_hu, self.base_hv, \
                                                self.base_H, \
                                                self.nx, self.ny, self.dx, self.dy, self.dt, \
                                                self.g, self.f, self.r, \
                                                wind_stress=wind, \
                                                boundary_conditions=self.boundaryConditions, \
                                                write_netcdf=False)
            if i == self.numParticles:
                # All particles done, only the observation is left,
                # and for the observation we only use one drifter, regardless of the
                # number in the other particles.
                driftersPerOceanModel = 1

            drifters = GPUDrifterCollection.GPUDrifterCollection(
                self.gpu_ctx,
                driftersPerOceanModel,
                observation_variance=self.observation_variance,
                boundaryConditions=self.boundaryConditions,
                domain_size_x=self.nx * self.dx,
                domain_size_y=self.ny * self.dy)
            initPos = np.random.multivariate_normal(
                self.midPoint, self.initialization_cov_drifters,
                driftersPerOceanModel)
            drifters.setDrifterPositions(initPos)
            #print "drifter particles: ", drifter.getParticlePositions()
            #print "drifter observations: ", drifter.getObservationPosition()
            self.particles[i].attachDrifters(drifters)

        # Put the initial positions into the observation array
        self._addObservation(self.observeTrueDrifters())
        print("Added init to observation array")
示例#5
0
    def attachDrifters(self, drifter_positions):
        for i in range(self.numParticles):
            # Attach drifters if requested
            self.logger.debug("Attaching %d drifters", len(drifter_positions))
            if (len(drifter_positions) > 0):
                drifters = GPUDrifterCollection.GPUDrifterCollection(
                    self.gpu_ctx,
                    len(drifter_positions),
                    observation_variance=self.observation_variance,
                    boundaryConditions=self.data_args['boundary_conditions'],
                    domain_size_x=self.data_args['nx'] * self.data_args['dx'],
                    domain_size_y=self.data_args['ny'] * self.data_args['dy'])
                drifters.setDrifterPositions(drifter_positions)
                self.particles[i].attachDrifters(drifters)

                self.drifterForecast[i] = Observation.Observation()
                self.drifterForecast[i].add_observation_from_sim(
                    self.particles[i])
示例#6
0
    def init(self):

        self.sim = CDKLM16.CDKLM16(self.gpu_ctx, \
                                   self.base_eta, self.base_hu, self.base_hv, \
                                   self.base_H, \
                                   self.nx, self.ny, self.dx, self.dy, self.dt, \
                                   self.g, self.f, self.r, \
                                   wind_stress=self.wind, \
                                   boundary_conditions=self.boundaryConditions, \
                                   write_netcdf=False)

        # TO CHECK! Is it okay to have drifters as self.drifters - in order to easier reach its member functions?
        self.drifters = GPUDrifterCollection.GPUDrifterCollection(self.gpu_ctx, self.numParticles,
                      observation_variance=self.observation_variance,
                      boundaryConditions=self.boundaryConditions,
                      domain_size_x=self.nx*self.dx, domain_size_y=self.ny*self.dy)
        
        self.drifters.initializeUniform()
        self.sim.attachDrifters(self.drifters)
示例#7
0
 def create_large_drifter_set(self, size, domain_x, domain_y):
     self.largeDrifterSet = GPUDrifterCollection(self.gpu_ctx,
                                                 size,
                                                 domain_size_x=domain_x,
                                                 domain_size_y=domain_y)
示例#8
0
 def create_resampling_drifter_set(self):
     self.resamplingDrifterSet = GPUDrifterCollection(
         self.gpu_ctx, self.resampleNumDrifters)
示例#9
0
 def create_small_drifter_set(self):
     self.smallDrifterSet = GPUDrifterCollection(self.gpu_ctx,
                                                 self.numDrifters,
                                                 self.observationVariance,
                                                 self.boundaryCondition)
示例#10
0
netcdf_iterations = int(
    (forecast_end_time - forecast_start_time) / netcdf_intervals)
observations_iterations = int(netcdf_intervals / observation_intervals)

for particle_id in range(ensemble.getNumParticles()):

    if ensemble.particlesActive[particle_id]:

        sim = ensemble.particles[particle_id]

        tic = time.time()
        next_obs_time = sim.t

        drifters = GPUDrifterCollection.GPUDrifterCollection(
            gpu_ctx,
            num_drifters,
            boundaryConditions=ensemble.getBoundaryConditions(),
            domain_size_x=ensemble.getDomainSizeX(),
            domain_size_y=ensemble.getDomainSizeY())
        drifters.setDrifterPositions(drifter_start_positions)
        sim.attachDrifters(drifters)

        forecast_file_name = forecastFileBase + str(particle_id).zfill(
            4) + ".bz2"

        observations = Observation.Observation()
        observations.add_observation_from_sim(sim)

        for netcdf_it in range(netcdf_iterations):

            for obs_it in range(observations_iterations):
                next_obs_time += observation_intervals
示例#11
0
def simulate_gpuocean_deterministic(source_url, domain, initx, inity, 
                                    sim_args, norkyst_data = True, erode_land = 1, 
                                    wind_drift_factor = 0.0, rescale=0,
                                    forecast_file = None, start_forecast_hours = 0, duration = 23, 
                                    ocean_state_file = None, netcdf_frequency = 5 ):
    """
    source_url: url or local file or list of either with fielddata in NetCDF-format
    domain: array/list on form [x0,x1,y0,y1] defining the domain for the simulation
    initx, inity = initial coordinates of single drifter or lists with coordinates for multiple drifters. 
                   In local cartesian coordinates of simulation-domain. 
    norkyst_data: (default True) If True, assumes data from norkyst800. Else, works with norfjords160m(and probably other ROMS data).
    sim_args, erode_land, observation_type: arguments needed for simulator and observation object. sim_args must be given.
    wind_drift_factor: fraction of wind-speed at which objects will be advected. Default is 0 (no direct wind-drift)
    rescale: factor setting resolution of simulation-grid. 0 indicates no rescaling(original resolution), 
             while any other number changes the resolution (ie 2 gives double resolution)
    forecast_file: optional file for storing trajectory (pickle)
    ocean_state_file: optional file for storing ocean state (netcdf)
    netcdf_frequency: frequency(in hours) for storing of ocean states. 
    start_forecast_hours = number hours after which to start simulating drifttrajectories(ocean model starts at beginning of field-data)
                           Default is at beginning of field-data. 
    forecast_duration = duration of simulation(including possibly only ocean simulation). Default is 24 hours.
    """

    end_forecast_hours = start_forecast_hours + duration
    
    #Create simulator
    data_args = NetCDFInitialization.getInitialConditions(source_url, domain[0], domain[1], domain[2],domain[3] , 
                     timestep_indices = None,norkyst_data = norkyst_data, erode_land = erode_land, download_data = False)
    
    if wind_drift_factor:
        wind_data = data_args.pop('wind', None)
    else:
        wind_data = None
        
    if rescale:
        data_args = NetCDFInitialization.rescaleInitialConditions(data_args, scale=rescale)

    sim = CDKLM16.CDKLM16(**sim_args, **NetCDFInitialization.removeMetadata(data_args))
    
    #Forecast
    observation_type = dautils.ObservationType.UnderlyingFlow 
    
    observation_args = {'observation_type': observation_type,
                    'nx': sim.nx, 'ny': sim.ny,
                    'domain_size_x': sim.nx*sim.dx,
                    'domain_size_y': sim.ny*sim.dy,
                    'land_mask': sim.getLandMask()
                   }

    trajectory_forecast = Observation.Observation(**observation_args)
    
    #Drifters
    #Assumes initx, inity same format/shape
    if type(initx) is not list:
        initx = [initx]
        inity = [inity]
    
    num_drifters = len(initx)
    
    drifters = GPUDrifterCollection.GPUDrifterCollection(sim_args['gpu_ctx'], num_drifters, wind = wind_data, 
                                                         wind_drift_factor = wind_drift_factor,
                                                     boundaryConditions = sim.boundary_conditions,
                                                     domain_size_x = trajectory_forecast.domain_size_x,
                                                     domain_size_y = trajectory_forecast.domain_size_y,
                                                     gpu_stream = sim.gpu_stream)
    
    drifter_pos_init = np.array([initx, inity]).T
        
    try:
        if ocean_state_file is not None:
            print("Storing ocean state to netCDF-file: " + ocean_state_file)
            ncfile = Dataset(ocean_state_file, 'w')

            var = {}
            var['eta'], var['hu'], var['hv'] = sim.download(interior_domain_only=False)
            _, var['Hm'] = sim.downloadBathymetry(interior_domain_only=False)

            ny, nx = var['eta'].shape

            # Create dimensions
            ncfile.createDimension('time', None) # unlimited
            ncfile.createDimension('x', nx)
            ncfile.createDimension('y', ny)

            ncvar = {}

            # Create variables for dimensions
            ncvar['time'] = ncfile.createVariable('time', 'f8', ('time',))
            ncvar['x'] = ncfile.createVariable('x', 'f4', ('x',))
            ncvar['y'] = ncfile.createVariable('y', 'f4', ('y',))

            # Fill dimension variables
            ncvar['x'][:] = np.linspace(0, nx*sim.dx, nx)
            ncvar['y'][:] = np.linspace(0, ny*sim.dy, ny)

            # Create static variables
            ncvar['Hm'] = ncfile.createVariable('Hm', 'f8', ('y', 'x',), zlib=True)
            ncvar['Hm'][:,:] = var['Hm'][:,:]

            # Create time varying data variables
            for varname in ['eta', 'hu', 'hv']:
                ncvar[varname] = ncfile.createVariable(varname, 'f8', ('time', 'y', 'x',), zlib=True)
            ncvar['num_iterations'] = ncfile.createVariable('num_iterations', 'i4', ('time',))

        #Run simulation
        num_total_hours = end_forecast_hours

        five_mins_in_an_hour = 12
        sub_dt = 5*60 # five minutes

        progress = Common.ProgressPrinter(5)
        pp = display(progress.getPrintString(0), display_id=True)

        netcdf_counter = 0
        for hour in range(num_total_hours):

            if hour == start_forecast_hours:
                # Attach drifters
                drifters.setDrifterPositions(drifter_pos_init)
                sim.attachDrifters(drifters)
                trajectory_forecast.add_observation_from_sim(sim)

            for mins in range(five_mins_in_an_hour):
                t = sim.step(sub_dt)
                if hour >= start_forecast_hours:
                    trajectory_forecast.add_observation_from_sim(sim)

            if ocean_state_file is not None and hour%netcdf_frequency == 0:
                var['eta'], var['hu'], var['hv'] = sim.download(interior_domain_only=False)
                ncvar['time'][netcdf_counter] = sim.t
                ncvar['num_iterations'][netcdf_counter] = sim.num_iterations

                abort=False
                for varname in ['eta', 'hu', 'hv']:
                    ncvar[varname][netcdf_counter,:,:] = var[varname][:,:] #np.ma.masked_invalid(var[varname][:,:])
                    if (np.any(np.isnan(var[varname]))):
                        print("Variable " + varname + " contains NaN values!")
                        abort=True
                netcdf_counter += 1

                if (abort):
                    print("Aborting at t=" + str(sim.t))
                    ncfile.sync()
                    break

            pp.update(progress.getPrintString(hour/(end_forecast_hours-1)))
    
        if forecast_file is not None:
            trajectory_forecast.to_pickle(forecast_file)
            
    except Exception as e:
        print("Something went wrong:" + str(e))
        raise e
    finally:
        if ocean_state_file is not None:
            ncfile.close()
        
    return trajectory_forecast
def simulate_gpuocean_deterministic(source_url,
                                    domain,
                                    initx,
                                    inity,
                                    sim_args,
                                    erode_land=1,
                                    wind_drift_factor=0.0,
                                    rescale=0,
                                    outfolder=None,
                                    start_forecast_hours=0,
                                    forecast_duration=23):
    """
    source_url: url or local file or list of either with fielddata in NetCDF-format
    domain: array/list on form [x0,x1,y0,y1] defining the domain for the simulation
    initx, inity = initial coordinates of single drifter or lists with coordinates for multiple drifters. 
                   In local cartesian coordinates of simulation-domain. 
    sim_args, erode_land, observation_type: arguments needed for simulator and observation object. sim_args must be given.
    wind_drift_factor: fraction of wind-speed at which objects will be advected. Default is 0 (no direct wind-drift)
    rescale: factor setting resolution of simulation-grid. 0 indicates no rescaling(original resolution), 
             while any other number changes the resolution (ie 2 gives double resolution)
    outfolder: outfolder
    start_forecast_hours = number hours after which to start simulating drifttrajectories(ocean model starts at beginning of field-data)
                           Default is at beginning of field-data. 
    forecast_duration = duration of simulation(including possibly only ocean simulation). Default is 24 hours.
    """

    end_forecast_hours = start_forecast_hours + forecast_duration

    #Create simulator
    data_args = NetCDFInitialization.getInitialConditions(
        source_url,
        domain[0],
        domain[1],
        domain[2],
        domain[3],
        timestep_indices=None,
        erode_land=erode_land,
        download_data=False)

    if wind_drift_factor:
        wind_data = data_args.pop('wind', None)
    else:
        wind_data = None

    if rescale:
        data_args = NetCDFInitialization.rescaleInitialConditions(
            data_args, scale=rescale)

    sim = CDKLM16.CDKLM16(**sim_args,
                          **NetCDFInitialization.removeMetadata(data_args))

    #Forecast
    observation_type = dautils.ObservationType.UnderlyingFlow

    observation_args = {
        'observation_type': observation_type,
        'nx': sim.nx,
        'ny': sim.ny,
        'domain_size_x': sim.nx * sim.dx,
        'domain_size_y': sim.ny * sim.dy,
        'land_mask': sim.getLandMask()
    }

    trajectory_forecast = Observation.Observation(**observation_args)

    if outfolder is not None:
        trajectory_forecast_filename = 'trajectory_forecast_' + str(
            start_forecast_hours) + '_to_' + str(
                end_forecast_hours) + '.pickle'

    #Drifters
    #Assumes initx, inity same format/shape
    if type(initx) is not list:
        initx = [initx]
        inity = [inity]

    num_drifters = len(initx)

    drifters = GPUDrifterCollection.GPUDrifterCollection(
        sim_args['gpu_ctx'],
        num_drifters,
        wind=wind_data,
        wind_drift_factor=wind_drift_factor,
        boundaryConditions=sim.boundary_conditions,
        domain_size_x=trajectory_forecast.domain_size_x,
        domain_size_y=trajectory_forecast.domain_size_y,
        gpu_stream=sim.gpu_stream)

    drifter_pos_init = np.array([initx, inity]).T

    #Run simulation
    num_total_hours = end_forecast_hours

    five_mins_in_an_hour = 12
    sub_dt = 5 * 60  # five minutes

    progress = Common.ProgressPrinter(5)
    pp = display(progress.getPrintString(0), display_id=True)

    for hour in range(num_total_hours):

        if hour == start_forecast_hours:
            # Attach drifters
            drifters.setDrifterPositions(drifter_pos_init)
            sim.attachDrifters(drifters)
            trajectory_forecast.add_observation_from_sim(sim)

        for mins in range(five_mins_in_an_hour):
            t = sim.step(sub_dt)
            if hour >= start_forecast_hours:
                trajectory_forecast.add_observation_from_sim(sim)

        pp.update(progress.getPrintString(hour / (end_forecast_hours - 1)))

    if outfolder is not None:
        trajectory_forecast.to_pickle(trajectory_forecast_path)

    return trajectory_forecast
示例#13
0
def generateTruth(gpu_ctx,
                  destination_dir,
                  duration_in_days=13,
                  duration_in_hours=0,
                  folder_name=None,
                  log_to_screen=False):
    """
    This funtion generates a truth simulation that will be the subject for 
    data assimilation experiments. It is based on the DoubleJetCase parameters 
    and initial conditions, and is (by default) spun up for 3 days before starting 
    to write its state to file. The generated data set should cover time range from
    day 3 to day 13.
    
    The end time of the truth is duration_in_days + duration_in_hours.
    """

    #--------------------------------------------------------------
    # PARAMETERS
    #--------------------------------------------------------------
    # This file takes no parameters, as it is should clearly define a specific truth.
    # If we come to a time where we need to specify a lot of different truths, we can introduce argparser again.

    # Time parameters
    start_time = 3 * 24 * 60 * 60  #  3 days
    end_time = (duration_in_days * 24 + duration_in_hours) * 60 * 60
    simulation_time = end_time - start_time
    observation_frequency = 5 * 60  # 5 minutes
    netcdf_frequency = 60 * 60  # every hour

    # Drifter parameters:
    num_drifters = 64

    assert (os.path.exists(destination_dir)
            ), 'destination_dir does not exist: ' + str(destination_dir)

    # File parameters:
    folder = os.path.join(
        destination_dir,
        "truth_" + datetime.datetime.now().strftime("%Y_%m_%d-%H_%M_%S"))
    if folder_name is not None:
        folder = os.path.join(destination_dir, folder_name)
    assert (not os.path.exists(folder)
            ), 'The directory ' + folder + ' already exists!'
    os.makedirs(folder)

    netcdf_filename = os.path.join(folder, "double_jet_case_truth.nc")
    drifter_filename = os.path.join(folder, "drifter_observations.pickle")

    if log_to_screen:
        print("------ Generating initial ensemble ---------------")
    if log_to_screen: print("Writing truth to file: " + netcdf_filename)

    # Create CUDA context
    device_name = gpu_ctx.cuda_device.name()

    #--------------------------------------------------------------
    # Creating the Case (including spin up)
    #--------------------------------------------------------------
    if log_to_screen: print("Initializing the truth")

    tic = time.time()
    sim = None
    doubleJetCase = None

    try:
        doubleJetCase = DoubleJetCase.DoubleJetCase(
            gpu_ctx, DoubleJetCase.DoubleJetPerturbationType.IEWPFPaperCase)

        doubleJetCase_args, doubleJetCase_init = doubleJetCase.getInitConditions(
        )

        if (np.any(np.isnan(doubleJetCase_init["eta0"]))):
            print(" `-> ERROR: Not a number in spinup, aborting!")
            raise RuntimeError('Not a number in spinup')

        toc = time.time()
        if log_to_screen:
            print("\n{:02.4f} s: ".format(toc - tic) +
                  "Generated initial conditions at day 3")

        #--------------------------------------------------------------
        # Initialize the truth from the Case (spin up is done in the Case)
        #--------------------------------------------------------------

        toc = time.time()
        if log_to_screen:
            print("\n{:02.4f} s: ".format(toc - tic) +
                  "Generated initial conditions for truth")

        #netcdf_args = {}
        netcdf_args = {
            'write_netcdf': True,
            'netcdf_filename': netcdf_filename
        }

        tic = time.time()
        sim = CDKLM16.CDKLM16(**doubleJetCase_args, **doubleJetCase_init,
                              **netcdf_args)

        toc = time.time()
        if log_to_screen:
            print("\n{:02.4f} s: ".format(toc - tic) +
                  "Truth simulator initiated")

        t = sim.t
        if log_to_screen:
            print("Three days = " + str(start_time) +
                  " seconds, but sim.t = " + str(sim.t) + ". Same? " +
                  str(start_time == sim.t))
        assert (round(start_time) == round(
            sim.t)), 'Spin up time seems to be wrong'

        #--------------------------------------------------------------
        # Create drifters at t = 3 days
        #--------------------------------------------------------------
        drifters = GPUDrifterCollection.GPUDrifterCollection(
            gpu_ctx,
            num_drifters,
            boundaryConditions=doubleJetCase_args['boundary_conditions'],
            domain_size_x=sim.nx * sim.dx,
            domain_size_y=sim.ny * sim.dy)
        sim.attachDrifters(drifters)

        #--------------------------------------------------------------
        # Create observation object and write the first drifter positions
        #--------------------------------------------------------------
        observations = Observation.Observation(domain_size_x=sim.nx * sim.dx,
                                               domain_size_y=sim.ny * sim.dy,
                                               nx=sim.nx,
                                               ny=sim.ny)

        # Configure observations to register static positions
        observations.setBuoyCellsByFrequency(25, 25)
        observations.add_observation_from_sim(sim)

        netcdf_iterations = int(simulation_time / netcdf_frequency)
        observation_sub_iterations = int(netcdf_frequency /
                                         observation_frequency)

        if log_to_screen:            print("We will now make " + str(netcdf_iterations) + " iterations with writing netcdf, and  " + \
str(observation_sub_iterations) + " subiterations with registering drifter positions.")

        theoretical_time = start_time

        ########################
        # Main simulation loop #
        ########################
        tic = time.time()

        time_error = 0

        for netcdf_it in range(netcdf_iterations):
            for observation_sub_it in range(observation_sub_iterations):

                next_obs_time = t + observation_frequency

                # Step until next observation
                sim.dataAssimilationStep(next_obs_time, write_now=False)

                # Store observation
                observations.add_observation_from_sim(sim)

                t = sim.t

                time_error += t - next_obs_time
                theoretical_time += observation_frequency

            sim.writeState()

            if netcdf_it % 10 == 0:

                # Check that everything looks okay
                eta, hu, hv = sim.download()
                if (np.any(np.isnan(eta))):
                    raise RuntimeError('Not a number at time ' + str(sim.t))

                sub_t = time.time() - tic
                if log_to_screen:
                    print("{:02.4f} s into loop: ".format(sub_t) +
                          "Done with netcdf iteration " + str(netcdf_it) +
                          " of " + str(netcdf_iterations))

        toc = time.time()
        if log_to_screen:
            print("{:02.4f} s: ".format(toc - tic) +
                  "Done with generating thruth")

        if log_to_screen: print("sim.t:            " + str(sim.t))

        ########################
        # Simulation loop DONE #
        ########################

        # Dump drifter observations to file:
        tic = time.time()
        observations.to_pickle(drifter_filename)
        toc = time.time()
        if log_to_screen:
            print("\n{:02.4f} s: ".format(toc - tic) +
                  "Drifter observations written to " + drifter_filename)

        return os.path.abspath(folder)

    except:

        raise

    finally:
        if sim is not None:
            sim.cleanUp()
        if doubleJetCase is not None:
            doubleJetCase.cleanUp()
        if log_to_screen:
            print("\n{:02.4f} s: ".format(toc - tic) +
                  "Clean up simulator done.")
示例#14
0
 def create_large_drifter_set(self, size, domain_x, domain_y):
     return GPUDrifterCollection(self.cl_ctx,
                                 size,
                                 domain_size_x=domain_x,
                                 domain_size_y=domain_y)