Commit 932c0f54 authored by Topi Rasku's avatar Topi Rasku
Browse files

Reorganizing the result calculation to improve performance by moving all...

Reorganizing the result calculation to improve performance by moving all possible calculations to the end of the solveloop.
parent 62432772
......@@ -35,6 +35,8 @@ r_totalRealizedCost
// State variable results, required for model structure !!!!!!!!!!!!!!!!!!!!!!!
r_state
// State variable slack results
r_stateSlack
// Energy transfer and spill variable results
r_transfer
......
......@@ -37,6 +37,8 @@ Parameters
// State variable results, required for model structure
r_state(grid, node, f, t) "Node state at timestep t"
// State variable slack values
r_stateSlack(grid, node, slack, f, t) "Note state slack at timestep t"
// Energy transfer and spill variable results
r_transfer(grid, from_node, to_node, f, t) "Energy transfer (MW)"
......
......@@ -34,24 +34,24 @@ r_online(uft_online(unit, ft_realized(f, t)))
+ v_online_MIP.l(unit, f, t)${ uft_onlineMIP(unit, f, t) }
;
// Reserve provisions of units
r_reserve(nuRescapable(restype, up_down, node, unit), f_solve(f), t_active(t))${ mft_nReserves(node, restype, mSolve, f, t)
or sum(f_, df_nReserves(node, restype, f_, t))
}
r_reserve(nuRescapable(restype, up_down, node, unit), f_solve(f), t_active(t))${ mft_nReserves(node, restype, mSolve, f, t)
or sum(f_, df_nReserves(node, restype, f_, t))
}
= v_reserve.l(restype, up_down, node, unit, f, t)
;
// Reserve transfer capacity
r_resTransferRightward(restypeDirectionNode(restype, up_down, from_node), to_node, f_solve(f), t_active(t))${ restypeDirectionNode(restype, up_down, to_node)
and [ mft_nReserves(from_node, restype, mSolve, f, t)
or sum(f_, df_nReserves(from_node, restype, f_, t))
]
}
r_resTransferRightward(restypeDirectionNode(restype, up_down, from_node), to_node, f_solve(f), t_active(t))${ restypeDirectionNode(restype, up_down, to_node)
and [ mft_nReserves(from_node, restype, mSolve, f, t)
or sum(f_, df_nReserves(from_node, restype, f_, t))
]
}
= v_resTransferRightward.l(restype, up_down, from_node, to_node, f, t)
;
r_resTransferLeftward(restypeDirectionNode(restype, up_down, from_node), to_node, f_solve(f), t_active(t))${ restypeDirectionNode(restype, up_down, to_node)
and [ mft_nReserves(from_node, restype, mSolve, f, t)
or sum(f_, df_nReserves(from_node, restype, f_, t))
]
}
r_resTransferLeftward(restypeDirectionNode(restype, up_down, from_node), to_node, f_solve(f), t_active(t))${ restypeDirectionNode(restype, up_down, to_node)
and [ mft_nReserves(from_node, restype, mSolve, f, t)
or sum(f_, df_nReserves(from_node, restype, f_, t))
]
}
= v_resTransferLeftward.l(restype, up_down, from_node, to_node, f, t)
;
// Unit startup and shutdown history
......@@ -61,8 +61,6 @@ r_startup(unit, starttype, ft_realized(f, t))${ uft_online(unit, f, t) }
r_shutdown(uft_online(unit, ft_realized(f, t)))
= v_shutdown.l(unit, f, t)
;
// Last realized timestep
*r_realizedLast = tRealizedLast;
* --- Interesting results -----------------------------------------------------
......@@ -74,10 +72,6 @@ r_gen(gnuft(grid, node, unit, ft_realized(f, t)))
r_fuelUse(fuel, uft(unit_fuel, ft_realized(f, t)))
= v_fuelUse.l(fuel, unit_fuel, f, t)
;
// Fuel used for generation
r_genFuel(gn(grid, node), fuel, ft_realized(f, t))
= sum(gnu(grid, node, unit), v_fuelUse.l(fuel, unit, f, t))
;
// Transfer of energy between nodes
r_transfer(gn2n(grid, from_node, to_node), ft_realized(f, t))
= v_transfer.l(grid, from_node, to_node, f, t)
......@@ -92,70 +86,15 @@ r_totalObj
;
// q_balance marginal values
r_balanceMarginal(gn(grid, node), ft_realized(f, t))
= 1e6 * q_balance.m(grid, node, mSolve, f, t)
= q_balance.m(grid, node, mSolve, f, t)
;
// q_resDemand marginal values
r_resDemandMarginal(restypeDirectionNode(restype, up_down, node), ft_realized(f, t))
= q_resDemand.m(restype, up_down, node, f, t)
;
* --- Realized system costs ---------------------------------------------------
r_gnRealizedCost(gn(grid, node), ft_realized(f, t))
// Time step length dependent costs
= 1e-6 // Scaling to MEUR
* [
// Time step length dependent costs
+ p_stepLength(mSolve, f, t)
* [
// Variable O&M costs
+ sum(gnuft(gnu_output(grid, node, unit), f, t), // Calculated only for output energy
+ v_gen.l(grid, node, unit, f, t)
* p_unit(unit, 'omCosts')
) // END sum(gnu_output)
// Fuel and emission costs
+ sum(uFuel(unit, 'main', fuel)${ gnuft(grid, node, unit, f, t) },
+ v_fuelUse.l(fuel, unit, f, t)
* [
+ ts_fuelPrice(fuel, t)
+ sum(emission, // Emission taxes
+ p_unitFuelEmissionCost(unit, fuel, emission)
) // END sum(emission)
] // END * v_fuelUse
) // END sum(uFuel)
// Node state slack variable penalties
+ sum(gn_stateSlack(grid, node),
+ sum(slack${p_gnBoundaryPropertiesForStates(grid, node, slack, 'slackCost')},
+ v_stateSlack.l(grid, node, slack, f, t)
* p_gnBoundaryPropertiesForStates(grid, node, slack, 'slackCost')
) // END sum(slack)
) // END sum(gn_stateSlack)
] // END * p_stepLength
// Start-up costs
+ sum(gnuft(grid, node, unit, f, t)${ uft_online(unit, f, t) },
+ sum(starttype,
+ v_startup.l(unit, starttype, f, t) // Cost of starting up
* [ // Startup variable costs
+ p_uStartup(unit, starttype, 'cost', 'unit')
// Start-up fuel and emission costs
+ sum(uFuel(unit, 'startup', fuel),
+ p_uStartup(unit, starttype, 'consumption', 'unit')${not unit_investLP(unit)}
* [
+ ts_fuelPrice(fuel, t)
+ sum(emission, // Emission taxes of startup fuel use
+ p_unitFuelEmissionCost(unit, fuel, emission)
) // END sum(emission)
] // END * p_uStartup
) // END sum(uFuel)
] // END * v_startup
) // END sum(starttype)
) // END sum(gnuft)
] // END * 1e-6
// v_stateSlack values for calculation of realized costs later on
r_stateSlack(gn_stateSlack(grid, node), slack, ft_realized(f, t))
= v_stateSlack.l(grid, node, slack, f, t)
;
* --- Feasibility results -----------------------------------------------------
......@@ -171,26 +110,7 @@ r_qResDemand(restypeDirectionNode(restype, up_down, node), ft_realized(f, t))
* --- Diagnostics Results -----------------------------------------------------
d_cop(uft(unit, ft_realized(f, t)))${sum(gnu_input(grid, node, unit), 1)}
= sum(gnu_output(grid, node, unit),
+ r_gen(grid, node, unit, f, t)
) // END sum(gnu_output)
/ [ sum(gnu_input(grid_, node_, unit),
-r_gen(grid_, node_, unit, f, t)
) // END sum(gnu_input)
+ 1${not sum(gnu_input(grid_, node_, unit), -r_gen(grid_, node_, unit, f, t))}
]
;
d_eff(uft(unit_fuel, ft_realized(f, t)))
= sum(gnu_output(grid, node, unit_fuel),
+ r_gen(grid, node, unit_fuel, f, t)
) // END sum(gnu_output)
/ [ sum(uFuel(unit_fuel, param_fuel, fuel),
+ r_fuelUse(fuel, unit_fuel, f, t)
) // END sum(uFuel)
+ 1${not sum(uFuel(unit_fuel, param_fuel, fuel), r_fuelUse(fuel, unit_fuel, f, t))}
]
;
// Capacity factors for examining forecast errors
d_capacityFactor(flow, node, f_solve(f), t_active(t))${ sum(flowUnit(flow, unit), nu(node, unit)) }
= ts_cf_(flow, node, f, t)
+ ts_cf(flow, node, f, t)${ not ts_cf_(flow, node, f, t) }
......
......@@ -16,14 +16,75 @@ along with Backbone. If not, see <http://www.gnu.org/licenses/>.
$offtext
* =============================================================================
* --- Time independent results ------------------------------------------------
* --- Time Step Dependent Results ---------------------------------------------
* =============================================================================
* --- Calculate time step length dependent results ----------------------------
// Need to loop over the model dimension, as this file is no longer contained in the modelSolves loop...
loop(m,
// Realized energy consumption !!! NOTE !!! This is a bit of an approximation at the moment
* --- Realized Nodal System Costs ---------------------------------------------
r_gnRealizedCost(gn(grid, node), ft_realizedNoReset(f, t))
// Time step length dependent costs
= 1e-6 // Scaling to MEUR
* [ // Time step length dependent costs
+ p_stepLengthNoReset(m, f, t)
* [
// Variable O&M costs
+ sum(gnu_output(grid, node, unit), // Calculated only for output energy
+ r_gen(grid, node, unit, f, t)
* p_unit(unit, 'omCosts')
) // END sum(gnu_output)
// Fuel and emission costs, allocated based on outputs
+ sum(uFuel(unit, 'main', fuel)${ gnu_output(grid, node, unit) },
+ r_fuelUse(fuel, unit, f, t)
* p_gnu(grid, node, unit, 'maxGen')
/ p_unit(unit, 'outputCapacityTotal')
* [
+ ts_fuelPrice(fuel, t)
+ sum(emission, // Emission taxes
+ p_unitFuelEmissionCost(unit, fuel, emission)
) // END sum(emission)
] // END * v_fuelUse
) // END sum(uFuel)
// Node state slack variable penalties
+ sum(gn_stateSlack(grid, node),
+ sum(slack${p_gnBoundaryPropertiesForStates(grid, node, slack, 'slackCost')},
+ r_stateSlack(grid, node, slack, f, t)
* p_gnBoundaryPropertiesForStates(grid, node, slack, 'slackCost')
) // END sum(slack)
) // END sum(gn_stateSlack)
] // END * p_stepLengthNoReset
// Start-up costs
+ sum(unitStarttype(unit, starttype)${ gnu_output(grid, node, unit) },
+ r_startup(unit, starttype, f, t) // Cost of starting up
* p_gnu(grid, node, unit, 'maxGen')
/ p_unit(unit, 'outputCapacityTotal')
* [ // Startup variable costs
+ p_uStartup(unit, starttype, 'cost', 'unit')
// Start-up fuel and emission costs
+ sum(uFuel(unit, 'startup', fuel),
+ p_uStartup(unit, starttype, 'consumption', 'unit')${not unit_investLP(unit)}
* [
+ ts_fuelPrice(fuel, t)
+ sum(emission, // Emission taxes of startup fuel use
+ p_unitFuelEmissionCost(unit, fuel, emission)
) // END sum(emission)
] // END * p_uStartup
) // END sum(uFuel)
] // END * r_startup
) // END sum(unitStarttype)
]; // END * 1e-6
* --- Realized Nodal Energy Consumption ---------------------------------------
// !!! NOTE !!! This is a bit of an approximation at the moment !!!!!!!!!!!!!!!
r_gnConsumption(gn(grid, node), ft_realizedNoReset(f, t))
= p_stepLengthNoReset(m, f, t)
* [
......@@ -33,12 +94,21 @@ loop(m,
) // END sum(gnu_input)
];
// Total generation on each node
* --- Total Energy Generation -------------------------------------------------
// Total energy generation
r_gnuTotalGen(gnu_output(grid, node, unit))
= sum(ft_realizedNoReset(f, t),
+ r_gen(grid, node, unit, f, t)
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
// Energy generation by fuels
r_genFuel(gn(grid, node), fuel, ft_realizedNoReset(f, t))
= sum(uFuel(unit, 'main', fuel)${ gnu_output(grid, node, unit) },
+ r_gen(grid, node, unit, f, t)
); // END sum(uFuel)
// Total generation on each node by fuels
r_gnTotalGenFuel(gn(grid, node), fuel)
= sum(ft_realizedNoReset(f, t),
......@@ -53,20 +123,26 @@ loop(m,
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
// Total transfer of energy between nodes
r_gnnTotalTransfer(gn2n(grid, from_node, to_node))
= sum(ft_realizedNoReset(f, t),
+ r_transfer(grid, from_node, to_node, f, t)
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
* --- Total Unit Online Results -----------------------------------------------
// Total energy spill from nodes
r_gnTotalSpill(grid, node_spill(node))
// Total sub-unit-hours for units over the simulation
r_uTotalOnline(unit)
= sum(ft_realizedNoReset(f, t),
+ r_spill(grid, node, f, t)
+ r_online(unit, f, t)
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
// Approximate utilization rates for gnus over the simulation
r_gnuUtilizationRate(gnu_output(grid, node, unit))
= r_gnuTotalGen(grid, node, unit)
/ [
+ p_gnu(grid, node, unit, 'maxGen')
* (mSettings(m, 't_end') - mSettings(m, 't_start') + 1)
* mSettings(m, 'intervalInHours')
]; // END division
* --- Total Reserve Provision -------------------------------------------------
// Total reserve provisions over the simulation
r_nuTotalReserve(nuRescapable(restype, up_down, node, unit))
= sum(ft_realizedNoReset(f, t),
......@@ -81,24 +157,38 @@ loop(m,
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
// Total sub-unit-hours for units over the simulation
r_uTotalOnline(unit)
* --- Total Transfer and Spill ------------------------------------------------
// Total transfer of energy between nodes
r_gnnTotalTransfer(gn2n(grid, from_node, to_node))
= sum(ft_realizedNoReset(f, t),
+ r_online(unit, f, t)
+ r_transfer(grid, from_node, to_node, f, t)
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
// Approximate utilization rates for gnus over the simulation
r_gnuUtilizationRate(gnu_output(grid, node, unit))
= r_gnuTotalGen(grid, node, unit)
/ [
+ p_gnu(grid, node, unit, 'maxGen')
* (mSettings(m, 't_end') - mSettings(m, 't_start') + 1)
* mSettings(m, 'intervalInHours')
]; // END division
// Total energy spill from nodes
r_gnTotalSpill(grid, node_spill(node))
= sum(ft_realizedNoReset(f, t),
+ r_spill(grid, node, f, t)
* p_stepLengthNoReset(m, f, t)
); // END sum(ft_realizedNoReset)
); // END loop(m)
* =============================================================================
* --- Futher Time Step Independent Results ------------------------------------
* =============================================================================
* --- Scaling Marginal Values to EUR/MWh --------------------------------------
// Energy balance
r_balanceMarginal(gn(grid, node), ft_realizedNoReset(f, t))
= 1e6 * r_balanceMarginal(grid, node, f, t);
// Reserve balance
r_resDemandMarginal(restypeDirectionNode(restype, up_down, node), ft_realizedNoReset(f, t))
= 1e6 * r_resDemandMarginal(restype, up_down, node, f, t);
* --- Total Generation Results ------------------------------------------------
// Total generation in gn
......@@ -151,9 +241,9 @@ r_totalGenFuel(fuel)
= sum(gn(grid, node), r_gnTotalGenFuel(grid, node, fuel));
// Total fuel consumption gn/g shares
r_gnTotalGenFuelShare(gn(grid, node), fuel)${ r_gTotalGenFuel(grid, fuel) }
r_gnTotalGenFuelShare(gn(grid, node), fuel)${ r_gnTotalGen(grid, node) }
= r_gnTotalGenFuel(grid, node, fuel)
/ r_gTotalGenFuel(grid, fuel);
/ r_gnTotalGen(grid, node);
* --- Total Spilled Energy Results --------------------------------------------
......@@ -214,5 +304,29 @@ r_uTotalShutdown(unit)
+ r_shutdown(unit, f, t)
); // END sum(ft_realizedNoReset)
* --- Diagnostic Results ------------------------------------------------------
// Estimated coefficients of performance
d_cop(unit, ft_realizedNoReset(f, t))${ sum(gnu_input(grid, node, unit), 1) }
= sum(gnu_output(grid, node, unit),
+ r_gen(grid, node, unit, f, t)
) // END sum(gnu_output)
/ [ sum(gnu_input(grid_, node_, unit),
-r_gen(grid_, node_, unit, f, t)
) // END sum(gnu_input)
+ 1${not sum(gnu_input(grid_, node_, unit), -r_gen(grid_, node_, unit, f, t))}
];
// Estimated efficiency
d_eff(unit_fuel(unit), ft_realizedNoReset(f, t))
= sum(gnu_output(grid, node, unit),
+ r_gen(grid, node, unit, f, t)
) // END sum(gnu_output)
/ [ sum(uFuel(unit, 'main', fuel),
+ r_fuelUse(fuel, unit, f, t)
) // END sum(uFuel)
+ 1${not sum(uFuel(unit, 'main', fuel), r_fuelUse(fuel, unit, f, t))}
];
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment