Skip to content

Commit

Permalink
Merge pull request #1331 from Renato-Rodrigues/emiMktTarget_update
Browse files Browse the repository at this point in the history
Emi mkt target update
  • Loading branch information
Renato-Rodrigues committed Jul 6, 2023
2 parents ac50de0 + d006d54 commit eafa7cd
Show file tree
Hide file tree
Showing 9 changed files with 100 additions and 57 deletions.
2 changes: 2 additions & 0 deletions core/sets.gms
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@
***-----------------------------------------------------------------------------
***-----------------------------------------------------------------------------
SETS
numberOrder "set to assure that numeric values follow ascending order in the GAMS entry order (e.g. iterations and years used in loop statements)" / 1*2200 /

* Save select compiler flags as sets, to make them accessible from the final gdx
c_expname "c_expname as set for use in GDX" /%c_expname%/
c_description "%c_description%" /"for model description, see explanatory text"/
Expand Down
11 changes: 11 additions & 0 deletions main.gms
Original file line number Diff line number Diff line change
Expand Up @@ -869,6 +869,17 @@ parameter
;
cm_postTargetIncrease = 0; !! def = 0
*'
parameter
cm_emiMktTarget_tolerance "tolerance for regipol emission target deviations convergence."
;
cm_emiMktTarget_tolerance = 0.01; !! def = 0.01, i.e. regipol emission targets must be met within 1% of target deviation
*' For budget targets the tolerance is measured relative to the target value. For year targets the tolerance is relative to 2005 emissions.
*'
parameter
cm_implicitQttyTarget_tolerance "tolerance for regipol implicit quantity target deviations convergence."
;
cm_implicitQttyTarget_tolerance = 0.01; !! def = 0.01, i.e. regipol implicit quantity targets must be met within 1% of target deviation
*'
parameter
cm_emiMktTargetDelay "number of years for delayed price change in the emission tax convergence algorithm. Not applied to first target set."
;
Expand Down
1 change: 1 addition & 0 deletions modules/47_regipol/none/not_used.txt
Original file line number Diff line number Diff line change
Expand Up @@ -74,3 +74,4 @@ vm_emiFgas,input,questionnaire
vm_emiMacSector,input,questionnaire
vm_emiTeDetailMkt,input,added by codeCheck
vm_emiTeMkt,input,added by codeCheck
cm_emiMktTarget_tolerance,switch,not needed
14 changes: 10 additions & 4 deletions modules/47_regipol/regiCarbonPrice/datainput.gms
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,16 @@ p47_implicitQttyTargetTaxRescale_iter("1", "2030",ext_regi,qttyTarget,qttyTarget
$endIf.cm_implicitQttyTarget

*** RR this should be replaced as soon as non-energy is treated endogenously in the model
*** EUR in 2030 ~ 90Mtoe (90 * 10^6 toe -> 90 * 10^6 toe * 41.868 GJ/toe -> 3768.12 * 10^6 GJ * 10^-9 EJ/GJ -> 3.76812 EJ * 1 TWa/31.536 EJ -> 0.1194863 TWa) EU27 = 92% EU28"
p47_nonEnergyUse("2030",ext_regi)$(sameas(ext_regi, "EUR_regi")) = 0.1194863;
p47_nonEnergyUse("2030",ext_regi)$(sameas(ext_regi, "EU27_regi")) = 0.11;

*** non-energy use values are calculated by taking the time path as contained in pm_fe_nechem.cs4r (where eg the 2030 value for EU27 is 91.6% of the 2020 value) and rescaling that with historic non-energy values from Eurostat
*** historical values can be found at: https://ec.europa.eu/eurostat/databrowser/bookmark/f7c8aa0e-3cf6-45d6-b85c-f2e76e90b4aa?lang=en
p47_nonEnergyUse("2030",ext_regi)$(sameas(ext_regi, "EU27_regi")) = 0.121606*0.916;
p47_nonEnergyUse("2030",ext_regi)$(sameas(ext_regi, "EUR_regi")) = 0.13*0.924;
p47_nonEnergyUse("2050",ext_regi)$(sameas(ext_regi, "EU27_regi")) = 0.121606*0.815;
p47_nonEnergyUse("2050",ext_regi)$(sameas(ext_regi, "EUR_regi")) = 0.13*0.841;

p47_nonEnergyUse("2030",ext_regi)$(sameas(ext_regi, "DEU")) = 0.03*0.928;
p47_nonEnergyUse("2045",ext_regi)$(sameas(ext_regi, "DEU")) = 0.03*0.848;
p47_nonEnergyUse("2050",ext_regi)$(sameas(ext_regi, "DEU")) = 0.03*0.822;
***--------------------------------------------------
*** Emission markets (EU Emission trading system and Effort Sharing)
***--------------------------------------------------
Expand Down
3 changes: 2 additions & 1 deletion modules/47_regipol/regiCarbonPrice/declarations.gms
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,13 @@ Parameter
*** Parameters necessary to calculate current emission target deviations
pm_emiMktCurrent(ttot,ttot2,ext_regi,emiMktExt) "previous iteration region emissions (from year ttot to ttot2 for budget) [GtCO2 or GtCO2eq]"
p47_emiMktCurrent_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) "parameter to save pm_emiMktCurrent across iterations [GtCO2 or GtCO2eq]"
pm_emiMktRefYear(ttot,ttot2,ext_regi,emiMktExt) "emissions in reference year 2015, used for calculating target deviation of year targets [GtCO2 or GtCO2eq]"
pm_emiMktRefYear(ttot,ttot2,ext_regi,emiMktExt) "emissions in reference year 2005, used for calculating target deviation of year targets [GtCO2 or GtCO2eq]"
pm_emiMktTarget_dev_iter(iteration, ttot,ttot2,ext_regi,emiMktExt) "parameter to save pm_emiMktTarget_dev across iterations [%]"

*** Parameters necessary to calculate the emission tax rescaling factor
p47_factorRescaleSlope(ttot,ttot2,ext_regi,emiMktExt) "auxiliary parameter to save the slope corresponding to the observed mitigation derivative regarding to co2tax level changes from the two previous iterations [#]"
p47_factorRescaleSlope_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) "parameter to save mitigation curve slope across iterations [#]"
p47_slopeReferenceIteration_iter(iteration,ttot,ext_regi) "auxiliary parameter to store reference iteration used for calculating slope of current mititgation cost [#]"
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) "multiplicative tax rescale factor that rescales emiMkt carbon price from iteration to iteration to reach regipol targets [%]"
p47_factorRescaleemiMktCO2Tax_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) "parameter to save rescale factor across iterations for debugging purposes [%]"

Expand Down
101 changes: 59 additions & 42 deletions modules/47_regipol/regiCarbonPrice/postsolve.gms
Original file line number Diff line number Diff line change
Expand Up @@ -194,8 +194,13 @@ pm_emiMktTarget_dev_iter(iteration, ttot,ttot2,ext_regi,emiMktExt) = pm_emiMktTa
loop((ext_regi,ttot2)$regiANDperiodEmiMktTarget_47(ttot2,ext_regi),
p47_targetConverged(ttot2,ext_regi) = 1;
loop((ttot,emiMktExt,target_type_47,emi_type_47)$((pm_emiMktTarget(ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47))),
if((abs(pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt)) > 0.01), !! if emiMKt target did not converged
p47_targetConverged(ttot2,ext_regi) = 0;
loop(regi$regi_groupExt(ext_regi,regi),
loop(emiMkt$emiMktGroup(emiMktExt,emiMkt),
*** if emiMKt target did not converged and we are not forcing negative prices (if the price is at minimal level (1$/tCO2) and current emissions are lower than the target)
if(((abs(pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt)) gt cm_emiMktTarget_tolerance) and (not ((pm_taxemiMkt(ttot2,regi,emiMkt) eq 1*sm_DptCO2_2_TDpGtC) and (pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt) lt 0)))), !! if emiMKt target did not converged and
p47_targetConverged(ttot2,ext_regi) = 0;
);
);
);
);
);
Expand All @@ -212,72 +217,84 @@ loop(ext_regi$regiEmiMktTarget(ext_regi),
);
p47_allTargetsConverged_iter(iteration,ext_regi) = p47_allTargetsConverged(ext_regi);

*** define current target to be solved
p47_currentConvergence_iter(iteration,ttot,ext_regi) = 0;
loop(ext_regi$regiEmiMktTarget(ext_regi),
*** solving targets sequentially, i.e. only apply target convergence algorithm if previous yearly targets were already achieved
if(not(p47_allTargetsConverged(ext_regi) eq 1), !!no rescale need if all targets already converged
*** define current target to be solved
loop((ttot)$regiANDperiodEmiMktTarget_47(ttot,ext_regi),
p47_currentConvergencePeriod(ext_regi) = ttot.val;
break$(p47_targetConverged(ttot,ext_regi) eq 0); !!only run target convergence up to the first year that has not converged
);
loop((ttot)$(regiANDperiodEmiMktTarget_47(ttot,ext_regi) and (ttot.val gt p47_currentConvergencePeriod(ext_regi))),
p47_nextConvergencePeriod(ext_regi) = ttot.val;
break;
);
loop((ttot,ttot2,emiMktExt,target_type_47,emi_type_47)$(pm_emiMktTarget(ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47) AND (ttot2.val eq p47_currentConvergencePeriod(ext_regi))),
p47_currentConvergence_iter(iteration,ttot2,ext_regi) = 1;
);
);
);

*** reference iteration from which to calculate the mitigation cost slope.
loop((ext_regi,ttot)$regiANDperiodEmiMktTarget_47(ttot,ext_regi),
if(ord(iteration) eq 1,
p47_slopeReferenceIteration_iter(iteration,ttot,ext_regi) = 1;
elseif(NOT(p47_currentConvergence_iter(iteration,ttot,ext_regi) eq p47_currentConvergence_iter(iteration-1,ttot,ext_regi))), !! reset the iteration reference for slope calculation if the target that is being analyzed changes
p47_slopeReferenceIteration_iter(iteration,ttot,ext_regi) = ord(iteration);
else
p47_slopeReferenceIteration_iter(iteration,ttot,ext_regi) = p47_slopeReferenceIteration_iter(iteration-1,ttot,ext_regi);
);
);


*** Calculating the emissions tax rescale factor based on previous iterations emission reduction
loop((ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47)$pm_emiMktTarget(ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47),
loop(emiMkt$emiMktGroup(emiMktExt,emiMkt),
loop(regi$regi_groupExt(ext_regi,regi),
*** initiliazing first iteration rescale factor based on remaining deviation
if(iteration.val eq 1,
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) = (1+pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt)) ** 2;
*** else if for the extreme case of a perfect match with no change between the two previous iteration emisssion taxes, in order to avoid a division by zero error, assume the rescale factor based on remaining deviation
elseif(((iteration.val eq 2) and (pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt) eq pm_taxemiMkt_iteration("1",ttot2,regi,emiMkt))) or
((iteration.val gt 2) and (pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt) eq pm_taxemiMkt_iteration("2",ttot2,regi,emiMkt)))),
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) = (1+pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt)) ** 2;
*** else using previous iteration information to define rescale factor
*** calculate rescale factor based on slope of previous iterations mitigation levels when compared to relative price difference
else
if(iteration.val eq 2,
p47_factorRescaleSlope(ttot,ttot2,ext_regi,emiMktExt) =
(p47_emiMktCurrent_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) - p47_emiMktCurrent_iter("1",ttot,ttot2,ext_regi,emiMktExt))
/
(pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt) - pm_taxemiMkt_iteration("1",ttot2,regi,emiMkt))
;
*** for iterations greater than 2, always calculate the slope relative to the second iteration
loop(iteration2$((iteration2.val le iteration.val) and (iteration2.val eq p47_slopeReferenceIteration_iter(iteration,ttot2,ext_regi))), !!reference iteration for slope calculation
*** if it is the first iteration or the reference iteration changed, initialize the rescale factor based on remaining deviation
if(iteration.val eq p47_slopeReferenceIteration_iter(iteration,ttot,ext_regi),
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) = (1+pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt)) ** 2;
*** else if for the extreme case of a perfect match with no change between the two iterations emisssion taxes used in the slope calculation, in order to avoid a division by zero error assume the rescale factor based on remaining deviation
elseif((pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt) eq pm_taxemiMkt_iteration(iteration2,ttot2,regi,emiMkt))),
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) = (1+pm_emiMktTarget_dev(ttot,ttot2,ext_regi,emiMktExt)) ** 2;
*** else, use previous iteration information to define rescale factor
else
*** calculate the slope of previous iterations mitigation levels when compared to relative price difference
p47_factorRescaleSlope(ttot,ttot2,ext_regi,emiMktExt) =
(p47_emiMktCurrent_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) - p47_emiMktCurrent_iter("2",ttot,ttot2,ext_regi,emiMktExt))
(p47_emiMktCurrent_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) - p47_emiMktCurrent_iter(iteration2,ttot,ttot2,ext_regi,emiMktExt))
/
(pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt) - pm_taxemiMkt_iteration("2",ttot2,regi,emiMkt))
(pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt) - pm_taxemiMkt_iteration(iteration2,ttot2,regi,emiMkt))
;
*** calculate the tax rescale factor using the above calculated slope
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) =
(
(pm_emiMktTarget(ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47) - p47_emiMktCurrent_iter(iteration,ttot,ttot2,ext_regi,emiMktExt))
/
(p47_factorRescaleSlope(ttot,ttot2,ext_regi,emiMktExt) * pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt))
) + 1;
);
*** emission tax rescale factor
pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt) =
(
(pm_emiMktTarget(ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47) - p47_emiMktCurrent_iter(iteration,ttot,ttot2,ext_regi,emiMktExt))
/
(p47_factorRescaleSlope(ttot,ttot2,ext_regi,emiMktExt) * pm_taxemiMkt_iteration(iteration,ttot2,regi,emiMkt))
) + 1;
);
);
);
);
p47_factorRescaleSlope_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) = p47_factorRescaleSlope(ttot,ttot2,ext_regi,emiMktExt);
p47_factorRescaleemiMktCO2Tax_iter(iteration,ttot,ttot2,ext_regi,emiMktExt) = pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt); !!save rescale factor across iterations for debugging of target convergence issues

p47_currentConvergence_iter(iteration,ttot,ext_regi) = 0;

loop(ext_regi$regiEmiMktTarget(ext_regi),
*** solving targets sequentially, i.e. only apply target convergence algorithm if previous yearly targets were already achieved
if(not(p47_allTargetsConverged(ext_regi) eq 1), !!no rescale need if all targets already converged
*** define current target to be solved
loop((ttot)$regiANDperiodEmiMktTarget_47(ttot,ext_regi),
p47_currentConvergencePeriod(ext_regi) = ttot.val;
break$(p47_targetConverged(ttot,ext_regi) eq 0); !!only run target convergence up to the first year that has not converged
);
loop((ttot)$(regiANDperiodEmiMktTarget_47(ttot,ext_regi) and (ttot.val gt p47_currentConvergencePeriod(ext_regi))),
p47_nextConvergencePeriod(ext_regi) = ttot.val;
break;
);
*** updating the emiMkt co2 tax for the first non converged yearly target
loop((ttot,ttot2,emiMktExt,target_type_47,emi_type_47)$(pm_emiMktTarget(ttot,ttot2,ext_regi,emiMktExt,target_type_47,emi_type_47) AND (ttot2.val eq p47_currentConvergencePeriod(ext_regi))),
p47_currentConvergence_iter(iteration,ttot2,ext_regi) = 1;
loop(emiMkt$emiMktGroup(emiMktExt,emiMkt),
loop(regi$regiEmiMktTarget2regi_47(ext_regi,regi),
*** terminal year price
if((iteration.val eq 1) and (pm_taxemiMkt(ttot2,regi,emiMkt) eq 0), !!intialize price for first iteration if it is missing
pm_taxemiMkt(ttot2,regi,emiMkt) = 1* sm_DptCO2_2_TDpGtC;
else !!update price using rescaling factor
pm_taxemiMkt(ttot2,regi,emiMkt) = pm_taxemiMkt(ttot2,regi,emiMkt) * pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt);
else !!update price using rescaling factor (Minimal aceptable price = 1 dollar/tCO2)
pm_taxemiMkt(ttot2,regi,emiMkt) = max(1* sm_DptCO2_2_TDpGtC, pm_taxemiMkt(ttot2,regi,emiMkt) * pm_factorRescaleemiMktCO2Tax(ttot,ttot2,ext_regi,emiMktExt));
);
*** linear price between first free year and current target terminal year
loop(ttot3,
Expand Down
Loading

0 comments on commit eafa7cd

Please sign in to comment.