@@ -2640,16 +2640,26 @@ def htcl_adj(self, measures_htcl_adj, adopt_scheme, htcl_adj_data):
26402640 "total" ][var_sub ][yr ]) * (
26412641 1 - adj_frac_t ) * fs_eff_splt_var
26422642 else :
2643- # Handle efficient-captured energy case for
2644- # fuel switching, where no base fuel data will
2645- # be reported (go to next variable in loop)
2643+ # Handle case where no base fuel data is reported, which is
2644+ # conceivable for fuel switching (go to next variable in loop)
26462645 try :
2647- adj_out_break [
2648- "base fuel" ][var ][var_sub ][yr ] = \
2649- adj_out_break ["base fuel" ][var ][
2650- var_sub ][yr ] - (
2651- adj [var ]["total" ][var_sub ][yr ]) * (
2652- 1 - adj_frac_t ) * fs_eff_splt_var
2646+ # Ensure baseline result is not already zero before
2647+ # adjusting; if zero, no further adjustment required
2648+ if (not isinstance (
2649+ adj_out_break ["base fuel" ][var ][var_sub ][yr ], numpy .ndarray )
2650+ and adj_out_break ["base fuel" ][var ][var_sub ][yr ] != 0 ) or (
2651+ isinstance (
2652+ adj_out_break ["base fuel" ][var ][var_sub ][yr ],
2653+ numpy .ndarray ) and all (adj_out_break [
2654+ "base fuel" ][var ][var_sub ][yr ]) != 0 ):
2655+ adj_out_break [
2656+ "base fuel" ][var ][var_sub ][yr ] = \
2657+ adj_out_break ["base fuel" ][var ][
2658+ var_sub ][yr ] - (
2659+ adj [var ]["total" ][var_sub ][yr ]) * (
2660+ 1 - adj_frac_t ) * fs_eff_splt_var
2661+ else :
2662+ continue
26532663 except KeyError :
26542664 continue
26552665
@@ -3862,15 +3872,23 @@ def compete_adj(
38623872 adj_key = "measure"
38633873 else :
38643874 adj_key = var_sub
3865- # Handle efficient-captured energy case for fuel switching,
3866- # where no base fuel data will be reported (skip to next
3867- # variable)
3875+ # Handle case where no base fuel data is reported, which is conceivable
3876+ # for fuel switching (go to next variable in loop)
38683877 try :
3869- adj_out_break ["base fuel" ][var ][var_sub ][yr ] = \
3870- adj_out_break ["base fuel" ][var ][
3871- var_sub ][yr ] - (
3872- adj [var ]["total" ][adj_key ][yr ]) * (
3873- 1 - adj_t ) * fs_eff_splt_var
3878+ # Ensure baseline result is not already zero before adjusting; if zero, no
3879+ # further adjustment required
3880+ if (not isinstance (
3881+ adj_out_break ["base fuel" ][var ][var_sub ][yr ], numpy .ndarray )
3882+ and adj_out_break ["base fuel" ][var ][var_sub ][yr ] != 0 ) or (
3883+ isinstance (adj_out_break ["base fuel" ][var ][var_sub ][yr ], numpy .ndarray )
3884+ and all (adj_out_break ["base fuel" ][var ][var_sub ][yr ]) != 0 ):
3885+ adj_out_break ["base fuel" ][var ][var_sub ][yr ] = \
3886+ adj_out_break ["base fuel" ][var ][
3887+ var_sub ][yr ] - (
3888+ adj [var ]["total" ][adj_key ][yr ]) * (
3889+ 1 - adj_t ) * fs_eff_splt_var
3890+ else :
3891+ continue
38743892 except KeyError :
38753893 continue
38763894
@@ -4995,6 +5013,95 @@ def finalize_outputs(
49955013 # the dict with these is calculated above
49965014 self .output_ecms [m .name ]["Markets and Savings (by Category)" ][
49975015 adopt_scheme ]["Stock Penetration (%)" ] = frac_mkt_stk
5016+ # If a user desires stock data as an output, calculate and report
5017+ # these data for the baseline and measure cases
5018+ if self .opts .report_stk is True :
5019+ # Set baseline and measure stock keys, including units that
5020+ # are calculated above
5021+ base_stk_uc_key , base_stk_c_key , meas_stk_key = [
5022+ x + stk_units for x in [
5023+ "Baseline Stock (Uncompeted)" ,
5024+ "Baseline Stock (Competed)" ,
5025+ "Measure Stock (Competed)" ]]
5026+ # Report baseline stock and stock cost figures (all baseline
5027+ # stock/stock cost that the measure could affect/capture);
5028+ # report both uncompeted/competed versions
5029+ stk_base_uc = {yr : m .markets [adopt_scheme ][
5030+ "uncompeted" ]["master_mseg" ]["stock" ][
5031+ "total" ]["all" ][yr ] for yr in focus_yrs }
5032+ stk_base_c = {
5033+ yr : mkts ["stock" ]["total" ]["all" ][yr ] for yr in focus_yrs }
5034+ stk_cost_base = {yr : mkts ["cost" ]["stock" ]["total" ][
5035+ "baseline" ][yr ] for yr in focus_yrs }
5036+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5037+ adopt_scheme ][base_stk_uc_key ] = stk_base_uc
5038+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5039+ adopt_scheme ][base_stk_c_key ] = stk_base_c
5040+ # Report measure stock and stock cost figures
5041+ stk_meas , stk_cost_meas = [{yr : mkts ["stock" ]["total" ][
5042+ "measure" ][yr ] for yr in focus_yrs },
5043+ {yr : mkts ["cost" ]["stock" ]["total" ][
5044+ "efficient" ][yr ] for yr in focus_yrs }]
5045+ # Calculate average and low/high measure stock and stock
5046+ # cost figures
5047+ stk_meas_avg , stk_cost_meas_avg = [{
5048+ k : numpy .mean (v ) for k , v in sv .items ()} for sv in [
5049+ stk_meas , stk_cost_meas ]]
5050+ stk_meas_low , stk_cost_meas_low = [{
5051+ k : numpy .percentile (v , 5 ) for k , v in sv .items ()} for sv
5052+ in [stk_meas , stk_cost_meas ]]
5053+ stk_meas_high , stk_cost_meas_high = [{
5054+ k : numpy .percentile (v , 95 ) for k , v in stk_meas .items ()}
5055+ for sv in [stk_meas , stk_cost_meas ]]
5056+ # Set the average measure stock output
5057+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5058+ adopt_scheme ][meas_stk_key ] = stk_meas_avg
5059+ # Set the average measure stock cost output
5060+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5061+ adopt_scheme ][stk_cost_key_tot ] = stk_cost_meas_avg
5062+ # Set the average measure incremental stock cost output
5063+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5064+ adopt_scheme ][stk_cost_key_inc ] = {
5065+ yr : (stk_cost_meas_avg [yr ] - stk_cost_base [yr ])
5066+ for yr in focus_yrs }
5067+ # Update stock cost data across all ECMs with data for
5068+ # current ECM
5069+ for yr in focus_yrs :
5070+ # Add to total stock cost data (first element of list)
5071+ stk_cost_all_ecms [0 ][yr ] += stk_cost_meas_avg [yr ]
5072+ # Add to inc. stock cost data (second element of list)
5073+ stk_cost_all_ecms [1 ][yr ] += (
5074+ stk_cost_meas_avg [yr ] - stk_cost_base [yr ])
5075+ # Set low/high measure stock outputs (as applicable)
5076+ if stk_meas_avg != stk_meas_low :
5077+ meas_stk_key_low , stk_cost_key_tot_low , \
5078+ stk_cost_key_inc_low = [x + " (low)" for x in [
5079+ meas_stk_key , stk_cost_key_tot , stk_cost_key_inc ]]
5080+ meas_stk_key_high , stk_cost_key_tot_high , \
5081+ stk_cost_key_inc_high = [x + " (high)" for x in [
5082+ meas_stk_key , stk_cost_key_tot , stk_cost_key_inc ]]
5083+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5084+ adopt_scheme ][meas_stk_key_low ] = stk_meas_low
5085+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5086+ adopt_scheme ][meas_stk_key_high ] = stk_meas_high
5087+ # Set the low measure stock cost output
5088+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5089+ adopt_scheme ][stk_cost_key_tot_low ] = \
5090+ stk_meas_low
5091+ # Set the low measure incremental stock cost output
5092+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5093+ adopt_scheme ][stk_cost_key_inc_low ] = {
5094+ yr : (stk_cost_meas_low [yr ] - stk_cost_base [yr ])
5095+ for yr in focus_yrs }
5096+ # Set the high measure stock cost output
5097+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5098+ adopt_scheme ][stk_cost_key_tot_high ] = \
5099+ stk_cost_meas_high
5100+ # Set the high measure incremental stock cost output
5101+ self .output_ecms [m .name ]["Markets and Savings (Overall)" ][
5102+ adopt_scheme ][stk_cost_key_inc_high ] = {
5103+ yr : (stk_cost_meas_high [yr ] - stk_meas_high [yr ])
5104+ for yr in focus_yrs }
49985105
49995106 # If a user desires output compatible with GCAM format, assess
50005107 # impacts of measures on GCAM baselines stock/energy segments.
0 commit comments