def load_scenario_models(self, scenario_list, scenario_data, timesteps): """Loads the scenario models into the system-of-systems model Note that we currently use the same name for the scenario name, and the name of the output of the ScenarioModel. Arguments --------- scenario_list : list A list of dicts with keys:: 'name': 'mass', 'spatial_resolution': 'country', 'temporal_resolution': 'seasonal', 'units': 'kg' scenario_data : dict A dict-of-list-of-dicts with keys ``param_name``: ``year``, ``region``, ``interval``, ``value`` timesteps : list Example ------- >>> builder = SosModelBuilder('test_sos_model') >>> model_list = [{'name': 'mass', 'spatial_resolution': 'country', 'temporal_resolution': 'seasonal', 'units': 'kg'}] >>> data = {'mass': [{'year': 2015, 'region': 'GB', 'interval': 'wet_season', 'value': 3}]} >>> timesteps = [2015, 2016] >>> builder.load_scenario_models(model_list, data, timesteps) """ self.logger.info("Loading scenarios") for scenario_meta in scenario_list: name = scenario_meta['name'] if name not in scenario_data: msg = "Parameter '{}' in scenario definitions not registered in scenario data" raise ValueError(msg.format(name)) scenario = ScenarioModel(name) spatial = scenario_meta['spatial_resolution'] temporal = scenario_meta['temporal_resolution'] spatial_res = self.region_register.get_entry(spatial) temporal_res = self.interval_register.get_entry(temporal) scenario.add_output(name, spatial_res, temporal_res, scenario_meta['units']) data = self._data_list_to_array(name, scenario_data[name], timesteps, spatial_res, temporal_res) scenario.add_data(data, timesteps) self.sos_model.add_model(scenario)
def get_scenario(): scenario = ScenarioModel('electricity_demand_scenario') scenario.add_output('electricity_demand_output', scenario.regions.get_entry('LSOA'), scenario.intervals.get_entry('annual'), 'unit') scenario.add_data(np.array([[[123]]]), [2010]) return scenario
def get_scenario_model_object(): data = np.array([[[3.]], [[5.]], [[1.]]], dtype=float) scenario_model = ScenarioModel('test_scenario_model') scenario_model.add_output('raininess', scenario_model.regions.get_entry('LSOA'), scenario_model.intervals.get_entry('annual'), 'ml') scenario_model.add_data(data, [2010, 2011, 2012]) return scenario_model
def test_model_set(self): elec_scenario = ScenarioModel('scenario') elec_scenario.add_output('output', elec_scenario.regions.get_entry('LSOA'), elec_scenario.intervals.get_entry('annual'), 'unit') elec_scenario.add_data(np.array([[[123]]]), [2010]) model_set = ModelSet([elec_scenario]) model_set.simulate(2010)
def test_scenario_dependencies(self): scenario_model = ScenarioModel('test_scenario') scenario_model.add_output('scenario_output', Mock(), Mock(), 'units') data = np.array([[[120.23]]]) timesteps = [2010] scenario_model.add_data(data, timesteps) model = EmptySectorModel('test_model') model.add_input('input_name', Mock(), Mock(), 'units') model.add_dependency(scenario_model, 'scenario_output', 'input_name') assert 'input_name' in model.deps assert model.get_scenario_data('input_name') == data
def test_dependency_not_present(self, get_sector_model): SectorModel = get_sector_model elec_scenario = ScenarioModel('scenario') elec_scenario.add_output('output', Mock(), Mock(), 'unit') elec_scenario.add_data(np.array([[[123]]]), [2010]) energy_model = SectorModel('model') energy_model.add_input('input', Mock(), Mock(), 'unit') with raises(ValueError): energy_model.add_dependency(elec_scenario, 'not_present', 'input') with raises(ValueError): energy_model.add_dependency(elec_scenario, 'output', 'not_correct_input_name')
def test_topological_sort(self, get_sector_model): SectorModel = get_sector_model elec_scenario = ScenarioModel('scenario') elec_scenario.add_output('output', Mock(), Mock(), 'unit') elec_scenario.add_data(np.array([[[123]]]), [2010]) energy_model = SectorModel('model') energy_model.add_input('input', Mock(), Mock(), 'unit') energy_model.add_dependency(elec_scenario, 'output', 'input') sos_model = SosModel('energy_sos_model') sos_model.add_model(energy_model) sos_model.add_model(elec_scenario) sos_model.check_dependencies() graph = sos_model.dependency_graph actual = networkx.topological_sort(graph, reverse=False) assert actual == [elec_scenario, energy_model]
def test_get_model_sets(self, get_sector_model): SectorModel = get_sector_model elec_scenario = ScenarioModel('scenario') elec_scenario.add_output('output', Mock(), Mock(), 'unit') elec_scenario.add_data(np.array([[[123]]]), [2010]) energy_model = SectorModel('model') energy_model.add_input('input', Mock(), Mock(), 'unit') energy_model.add_dependency(elec_scenario, 'output', 'input') sos_model = SosModel('energy_sos_model') sos_model.add_model(energy_model) sos_model.add_model(elec_scenario) sos_model.check_dependencies() actual = sos_model._get_model_sets_in_run_order() expected = ['scenario', 'model'] for model, name in zip(actual, expected): assert model.name == name
def test_simple_graph(self, get_sector_model): SectorModel = get_sector_model elec_scenario = ScenarioModel('scenario') elec_scenario.add_output('output', Mock(), Mock(), 'unit') elec_scenario.add_data(np.array([[[123]]]), [2010]) energy_model = SectorModel('model') energy_model.add_input('input', Mock(), Mock(), 'unit') energy_model.add_dependency(elec_scenario, 'output', 'input') sos_model = SosModel('energy_sos_model') sos_model.add_model(energy_model) sos_model.add_model(elec_scenario) # Builds the dependency graph sos_model.check_dependencies() graph = sos_model.dependency_graph assert energy_model in graph assert elec_scenario in graph assert graph.edges() == [(elec_scenario, energy_model)]
def test_composite_nested_sos_model(self, get_sector_model): """System of systems example with two nested SosModels, two Scenarios and one SectorModel. One dependency is defined at the SectorModel level, another at the lower SosModel level """ SectorModel = get_sector_model elec_scenario = ScenarioModel('electricity_demand_scenario') elec_scenario.add_output('electricity_demand_output', Mock(), Mock(), 'unit') elec_scenario.add_data(np.array([[[123]]]), [2010]) energy_model = SectorModel('energy_sector_model') energy_model.add_input('electricity_demand_input', Mock(), Mock(), 'unit') energy_model.add_input('fluffiness_input', Mock(), Mock(), 'unit') energy_model.add_output('cost', Mock(), Mock(), 'unit') energy_model.add_output('fluffyness', Mock(), Mock(), 'unit') def energy_function(timestep, input_data): """Mimics the running of a sector model """ results = {} demand = input_data['electricity_demand_input'] fluff = input_data['fluffiness_input'] results['cost'] = demand * 1.2894 results['fluffyness'] = fluff * 22 return results energy_model.simulate = energy_function energy_model.add_dependency(elec_scenario, 'electricity_demand_output', 'electricity_demand_input') sos_model_lo = SosModel('lower') sos_model_lo.add_model(elec_scenario) sos_model_lo.add_model(energy_model) fluf_scenario = ScenarioModel('fluffiness_scenario') fluf_scenario.add_output('fluffiness', Mock(), Mock(), 'unit') fluf_scenario.add_data(np.array([[[12]]]), [2010]) assert sos_model_lo.free_inputs.names == ['fluffiness_input'] sos_model_lo.add_dependency(fluf_scenario, 'fluffiness', 'fluffiness_input') assert sos_model_lo.model_inputs.names == [] sos_model_high = SosModel('higher') sos_model_high.add_model(sos_model_lo) sos_model_high.add_model(fluf_scenario) actual = sos_model_high.simulate(2010) expected = { 'fluffiness_scenario': { 'fluffiness': 12 }, 'lower': { 'electricity_demand_scenario': { 'electricity_demand_output': 123 }, 'energy_sector_model': { 'cost': 158.5962, 'fluffyness': 264 } } } assert actual == expected