Skip to content

Commit 50c1346

Browse files
Merge pull request #287 from idelder/dsd_periods
2 parents 3e29e07 + 6bdda77 commit 50c1346

14 files changed

Lines changed: 172 additions & 92 deletions

File tree

temoa/_internal/table_data_puller.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -189,7 +189,7 @@ def poll_flow_results(model: TemoaModel, epsilon: float = 1e-5) -> dict[FI, dict
189189
for s in model.time_season:
190190
for d in model.time_of_day:
191191
if o in model.commodity_demand:
192-
distribution = value(model.demand_specific_distribution[r, s, d, o])
192+
distribution = value(model.demand_specific_distribution[r, p, s, d, o])
193193
else:
194194
distribution = value(model.segment_fraction[s, d])
195195
fi = FI(r, p, s, d, i, t, v, o)

temoa/components/capacity.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -428,7 +428,7 @@ def capacity_constraint(
428428
# Annual demand technology
429429
useful_activity = sum(
430430
(
431-
value(model.demand_specific_distribution[r, s, d, S_o])
431+
value(model.demand_specific_distribution[r, p, s, d, S_o])
432432
if S_o in model.commodity_demand
433433
else value(model.segment_fraction[s, d])
434434
)

temoa/components/commodities.py

Lines changed: 16 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,7 @@ def check_singleton_demands(model: TemoaModel) -> None:
117117
model.v_flow_out_annual[r, p, i, t, v, dem].fix(val)
118118
if t not in model.tech_annual:
119119
for s, d in cross_product(model.time_season, model.time_of_day):
120-
dsd = value(model.demand_specific_distribution[r, s, d, dem])
120+
dsd = value(model.demand_specific_distribution[r, p, s, d, dem])
121121
model.v_flow_out[r, p, s, d, i, t, v, dem].fix(val * dsd)
122122
model.singleton_demands.add((r, p, dem))
123123

@@ -279,7 +279,7 @@ def demand_activity_constraint(
279279
for s_i in model.process_inputs_by_output[r, p, t, v, dem]
280280
)
281281

282-
expr = annual_activity * value(model.demand_specific_distribution[r, s, d, dem]) == activity
282+
expr = annual_activity * value(model.demand_specific_distribution[r, p, s, d, dem]) == activity
283283
return expr
284284

285285

@@ -416,7 +416,7 @@ def commodity_balance_constraint(
416416
# Into annual flows
417417
consumed += sum(
418418
(
419-
value(model.demand_specific_distribution[r, s, d, s_o])
419+
value(model.demand_specific_distribution[r, p, s, d, s_o])
420420
if s_o in model.commodity_demand
421421
else value(model.segment_fraction[s, d])
422422
)
@@ -722,10 +722,11 @@ def create_demands(model: TemoaModel) -> None:
722722
logger.debug('Started creating demand distributions in CreateDemands()')
723723

724724
# Step 0: some setup for a couple of reusable items
725-
# Get the nth element from the tuple (r, s, d, dem)
725+
# Get the nth element from the tuple (r, p, s, d, dem))
726726
# So we only have to update these indices in one place if they change
727727
demand_specific_distribution_region = iget(0)
728-
demand_specific_distributon_dem = iget(3)
728+
demand_specific_distributon_period = iget(1)
729+
demand_specific_distributon_dem = iget(4)
729730

730731
# Step 1: Check if any demand commodities are going unused
731732
used_dems = {dem for _r, _p, dem in model.demand.sparse_keys()}
@@ -794,27 +795,29 @@ def create_demands(model: TemoaModel) -> None:
794795
unset_distributions = set(
795796
cross_product(
796797
model.regions,
798+
model.time_optimize,
797799
model.time_season,
798800
model.time_of_day,
799801
unset_demand_distributions,
800802
)
801803
)
802-
for r, s, d, dem in unset_distributions:
803-
demand_specific_distribution[r, s, d, dem] = value(
804+
for r, p, s, d, dem in unset_distributions:
805+
demand_specific_distribution[r, p, s, d, dem] = value(
804806
model.segment_fraction[s, d]
805807
) # DSD._constructed = True
806808

807809
# Step 5: A final "sum to 1" check for all DSD members (which now should be everything)
808810
# Also check that all keys are made... The demand distro should be supported
809811
# by the full set of (r, p, dem) keys because it is an equality constraint
810812
# and we need to ensure even the zeros are passed in
811-
used_r_dems = {(r, dem) for r, p, dem in model.demand.sparse_keys()}
812-
for r, dem in used_r_dems:
813+
used_rp_dems = {(r, p, dem) for r, p, dem in model.demand.sparse_keys()}
814+
for r, p, dem in used_rp_dems:
813815
expected_key_length = len(model.time_season) * len(model.time_of_day)
814816
keys = [
815817
k
816818
for k in demand_specific_distribution.sparse_keys()
817819
if demand_specific_distribution_region(k) == r
820+
and demand_specific_distributon_period(k) == p
818821
and demand_specific_distributon_dem(k) == dem
819822
]
820823
if len(keys) != expected_key_length:
@@ -823,11 +826,11 @@ def create_demands(model: TemoaModel) -> None:
823826
(s, d)
824827
for s in model.time_season
825828
for d in model.time_of_day
826-
if (r, s, d, dem) not in keys
829+
if (r, p, s, d, dem) not in keys
827830
}
828831
logger.info(
829832
'Missing some time slices for Demand Specific Distribution %s: %s',
830-
(r, dem),
833+
(r, p, dem),
831834
missing,
832835
)
833836
total = sum(value(demand_specific_distribution[i]) for i in keys)
@@ -855,7 +858,7 @@ def get_str_padding(obj: Any) -> int:
855858
'must total to 1.\n\n Demand-specific distribution in error: '
856859
' \n {}\n\tsum = {}'
857860
)
858-
logger.error(msg.format((r, dem), items, total))
859-
raise ValueError(msg.format((r, dem), items, total))
861+
logger.error(msg.format((r, p, dem), items, total))
862+
raise ValueError(msg.format((r, p, dem), items, total))
860863

861864
logger.debug('Finished creating demand distributions')

temoa/components/emissions.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,7 @@ def linked_emissions_tech_constraint(
107107
if t in model.tech_annual:
108108
primary_flow = quicksum(
109109
(
110-
value(model.demand_specific_distribution[r, s, d, S_o])
110+
value(model.demand_specific_distribution[r, p, s, d, S_o])
111111
if S_o in model.commodity_demand
112112
else value(model.segment_fraction[s, d])
113113
)
@@ -135,7 +135,7 @@ def linked_emissions_tech_constraint(
135135
if linked_t in model.tech_annual:
136136
linked_flow = quicksum(
137137
(
138-
value(model.demand_specific_distribution[r, s, d, S_o])
138+
value(model.demand_specific_distribution[r, p, s, d, S_o])
139139
if S_o in model.commodity_demand
140140
else value(model.segment_fraction[s, d])
141141
)

temoa/components/reserves.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -313,7 +313,7 @@ def reserve_margin_constraint(
313313
# Annual generation
314314
total_generation += sum(
315315
(
316-
value(model.demand_specific_distribution[r, s, d, S_o])
316+
value(model.demand_specific_distribution[r, p, s, d, S_o])
317317
if S_o in model.commodity_demand
318318
else value(model.segment_fraction[s, d])
319319
)

temoa/core/model.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -360,6 +360,7 @@ def __init__(self, *args: object, **kwargs: object) -> None:
360360
# )
361361
self.demand_specific_distribution = Param(
362362
self.regions,
363+
self.time_optimize,
363364
self.time_season,
364365
self.time_of_day,
365366
self.commodity_demand,

temoa/data_io/component_manifest.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -386,8 +386,8 @@ def build_manifest(model: TemoaModel) -> list[LoadItem]:
386386
LoadItem(
387387
component=model.demand_specific_distribution,
388388
table='demand_specific_distribution',
389-
columns=['region', 'season', 'tod', 'demand_name', 'dsd'],
390-
is_period_filtered=False,
389+
columns=['region', 'period', 'season', 'tod', 'demand_name', 'dsd'],
390+
is_period_filtered=True,
391391
is_table_required=False,
392392
),
393393
LoadItem(

temoa/db_schema/temoa_schema_v4.sql

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -208,6 +208,8 @@ CREATE TABLE IF NOT EXISTS demand
208208
CREATE TABLE IF NOT EXISTS demand_specific_distribution
209209
(
210210
region TEXT,
211+
period INTEGER
212+
REFERENCES time_period (period),
211213
season TEXT
212214
REFERENCES time_season (season),
213215
tod TEXT
@@ -216,7 +218,7 @@ CREATE TABLE IF NOT EXISTS demand_specific_distribution
216218
REFERENCES commodity (name),
217219
dsd REAL,
218220
notes TEXT,
219-
PRIMARY KEY (region, season, tod, demand_name),
221+
PRIMARY KEY (region, period, season, tod, demand_name),
220222
CHECK (dsd >= 0 AND dsd <= 1)
221223
);
222224
CREATE TABLE IF NOT EXISTS end_of_life_output

temoa/tutorial_assets/utopia.sql

Lines changed: 33 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -398,6 +398,8 @@ INSERT INTO "demand" VALUES('utopia',2010,'TX',11.69,'PJ','');
398398
CREATE TABLE demand_specific_distribution
399399
(
400400
region TEXT,
401+
period INTEGER
402+
REFERENCES time_period (period),
401403
season TEXT
402404
REFERENCES time_season (season),
403405
tod TEXT
@@ -406,19 +408,39 @@ CREATE TABLE demand_specific_distribution
406408
REFERENCES commodity (name),
407409
dsd REAL,
408410
notes TEXT,
409-
PRIMARY KEY (region, season, tod, demand_name),
411+
PRIMARY KEY (region, period, season, tod, demand_name),
410412
CHECK (dsd >= 0 AND dsd <= 1)
411413
);
412-
INSERT INTO "demand_specific_distribution" VALUES('utopia','inter','day','RH',0.12,'');
413-
INSERT INTO "demand_specific_distribution" VALUES('utopia','inter','night','RH',0.06,'');
414-
INSERT INTO "demand_specific_distribution" VALUES('utopia','winter','day','RH',0.5467,'');
415-
INSERT INTO "demand_specific_distribution" VALUES('utopia','winter','night','RH',0.2733,'');
416-
INSERT INTO "demand_specific_distribution" VALUES('utopia','inter','day','RL',0.15,'');
417-
INSERT INTO "demand_specific_distribution" VALUES('utopia','inter','night','RL',0.05,'');
418-
INSERT INTO "demand_specific_distribution" VALUES('utopia','summer','day','RL',0.15,'');
419-
INSERT INTO "demand_specific_distribution" VALUES('utopia','summer','night','RL',0.05,'');
420-
INSERT INTO "demand_specific_distribution" VALUES('utopia','winter','day','RL',0.5,'');
421-
INSERT INTO "demand_specific_distribution" VALUES('utopia','winter','night','RL',0.1,'');
414+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'inter','day','RH',0.12,'');
415+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'inter','night','RH',0.06,'');
416+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'winter','day','RH',0.5467,'');
417+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'winter','night','RH',0.2733,'');
418+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'inter','day','RL',0.15,'');
419+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'inter','night','RL',0.05,'');
420+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'summer','day','RL',0.15,'');
421+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'summer','night','RL',0.05,'');
422+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'winter','day','RL',0.5,'');
423+
INSERT INTO "demand_specific_distribution" VALUES('utopia',1990,'winter','night','RL',0.1,'');
424+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'inter','day','RH',0.12,'');
425+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'inter','night','RH',0.06,'');
426+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'winter','day','RH',0.5467,'');
427+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'winter','night','RH',0.2733,'');
428+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'inter','day','RL',0.15,'');
429+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'inter','night','RL',0.05,'');
430+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'summer','day','RL',0.15,'');
431+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'summer','night','RL',0.05,'');
432+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'winter','day','RL',0.5,'');
433+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2000,'winter','night','RL',0.1,'');
434+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'inter','day','RH',0.12,'');
435+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'inter','night','RH',0.06,'');
436+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'winter','day','RH',0.5467,'');
437+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'winter','night','RH',0.2733,'');
438+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'inter','day','RL',0.15,'');
439+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'inter','night','RL',0.05,'');
440+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'summer','day','RL',0.15,'');
441+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'summer','night','RL',0.05,'');
442+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'winter','day','RL',0.5,'');
443+
INSERT INTO "demand_specific_distribution" VALUES('utopia',2010,'winter','night','RL',0.1,'');
422444
CREATE TABLE efficiency
423445
(
424446
region TEXT,

tests/testing_data/mediumville.sql

Lines changed: 16 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -64,22 +64,22 @@ REPLACE INTO "demand" VALUES('A',2025,'RL',100.0,'','');
6464
REPLACE INTO "demand" VALUES('B',2025,'RL',100.0,NULL,NULL);
6565
REPLACE INTO "demand" VALUES('A',2025,'RH',50.0,NULL,NULL);
6666
REPLACE INTO "demand" VALUES('B',2025,'RH',50.0,NULL,NULL);
67-
REPLACE INTO "demand_specific_distribution" VALUES('A','s1','d1','RL',0.25,NULL);
68-
REPLACE INTO "demand_specific_distribution" VALUES('A','s1','d2','RL',0.25,NULL);
69-
REPLACE INTO "demand_specific_distribution" VALUES('A','s2','d1','RL',0.25,NULL);
70-
REPLACE INTO "demand_specific_distribution" VALUES('A','s2','d2','RL',0.25,NULL);
71-
REPLACE INTO "demand_specific_distribution" VALUES('B','s1','d1','RL',0.25,NULL);
72-
REPLACE INTO "demand_specific_distribution" VALUES('B','s1','d2','RL',0.25,NULL);
73-
REPLACE INTO "demand_specific_distribution" VALUES('B','s2','d1','RL',0.25,NULL);
74-
REPLACE INTO "demand_specific_distribution" VALUES('B','s2','d2','RL',0.25,NULL);
75-
REPLACE INTO "demand_specific_distribution" VALUES('A','s1','d1','RH',0.25,NULL);
76-
REPLACE INTO "demand_specific_distribution" VALUES('A','s2','d1','RH',0.25,NULL);
77-
REPLACE INTO "demand_specific_distribution" VALUES('B','s1','d1','RH',0.25,NULL);
78-
REPLACE INTO "demand_specific_distribution" VALUES('B','s2','d1','RH',0.25,NULL);
79-
REPLACE INTO "demand_specific_distribution" VALUES('A','s1','d2','RH',0.25,NULL);
80-
REPLACE INTO "demand_specific_distribution" VALUES('A','s2','d2','RH',0.25,NULL);
81-
REPLACE INTO "demand_specific_distribution" VALUES('B','s1','d2','RH',0.25,NULL);
82-
REPLACE INTO "demand_specific_distribution" VALUES('B','s2','d2','RH',0.25,NULL);
67+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s1','d1','RL',0.25,NULL);
68+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s1','d2','RL',0.25,NULL);
69+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s2','d1','RL',0.25,NULL);
70+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s2','d2','RL',0.25,NULL);
71+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s1','d1','RL',0.25,NULL);
72+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s1','d2','RL',0.25,NULL);
73+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s2','d1','RL',0.25,NULL);
74+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s2','d2','RL',0.25,NULL);
75+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s1','d1','RH',0.25,NULL);
76+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s2','d1','RH',0.25,NULL);
77+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s1','d1','RH',0.25,NULL);
78+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s2','d1','RH',0.25,NULL);
79+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s1','d2','RH',0.25,NULL);
80+
REPLACE INTO "demand_specific_distribution" VALUES('A',2025,'s2','d2','RH',0.25,NULL);
81+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s1','d2','RH',0.25,NULL);
82+
REPLACE INTO "demand_specific_distribution" VALUES('B',2025,'s2','d2','RH',0.25,NULL);
8383
REPLACE INTO "efficiency" VALUES('A', 'ELC', 'bulbs', 2025, 'RL', 1.0, NULL, NULL);
8484
REPLACE INTO "efficiency" VALUES('A', 'HYD', 'EH', 2025, 'ELC', 1.0, NULL, NULL);
8585
REPLACE INTO "efficiency" VALUES('A', 'HYD', 'EF', 2025, 'ELC', 1.0, NULL, NULL);

0 commit comments

Comments
 (0)