From 3ca488798cb4e0ad3ecf263b3eec676ed3ecaf8d Mon Sep 17 00:00:00 2001 From: Fabian Neumann Date: Thu, 14 Nov 2019 16:15:42 +0100 Subject: [PATCH] Emission price option `Ep reactivated (#100) * prepare_network: reactivate Ep option (closes #63) * doc: update documentation on Ep option --- doc/configtables/costs.csv | 4 ++-- doc/configtables/opts.csv | 4 ++-- scripts/add_electricity.py | 13 ------------- scripts/prepare_network.py | 10 ++++------ 4 files changed, 8 insertions(+), 23 deletions(-) diff --git a/doc/configtables/costs.csv b/doc/configtables/costs.csv index c35b83dc..383a6423 100644 --- a/doc/configtables/costs.csv +++ b/doc/configtables/costs.csv @@ -4,5 +4,5 @@ discountrate,--,float,"Default discount rate if not specified for a technology i USD2013_to_EUR2013,--,float,"Exchange rate from USD :math:`_{2013}` to EUR :math:`_{2013}` from `ECB `_" capital_cost,EUR/MW,"Keys should be in the 'technology' column of ``data/costs.csv``. Values can be any float.","For the given technologies, assumptions about their capital investment costs are set to the corresponding value. Optional; overwrites cost assumptions from ``data/costs.csv``." marginal_cost,EUR/MWh,"Keys should be in the 'technology' column of ``data/costs.csv``. Values can be any float.","For the given technologies, assumptions about their marginal operating costs are set to the corresponding value. Optional; overwrites cost assumptions from ``data/costs.csv``." -emission_prices,,, --- co2,EUR/t,float,"Exogenous price of carbon-dioxide added to the marginal costs of fossil-fuelled generators according to their carbon intensity." \ No newline at end of file +emission_prices,,,"Specify exogenous prices for emission types listed in ``network.carriers`` to marginal costs." +-- co2,EUR/t,float,"Exogenous price of carbon-dioxide added to the marginal costs of fossil-fuelled generators according to their carbon intensity. Added through the keyword ``Ep`` in the ``{opts}`` wildcard only in the rule :mod:`prepare_network``." \ No newline at end of file diff --git a/doc/configtables/opts.csv b/doc/configtables/opts.csv index 6723a103..5753fb37 100644 --- a/doc/configtables/opts.csv +++ b/doc/configtables/opts.csv @@ -1,7 +1,7 @@ Trigger, Description, Definition, Status -``Co2L``, Add an overall absolute carbon-dioxide emissions limit configured in ``electricity: co2limit``. If a float is appended an overall emission limit relative to the emission level given in ``electricity: co2base`` is added (e.g. ``Co2L0.05`` limits emissisions to 5% of what is given in ``electricity: co2base``), ``prepare_network``: `add_co2limit() `_ and its `caller `_, In active use ``nH``; i.e. ``2H``-``6H``, Resample the time-resolution by averaging over every ``n`` snapshots, ``prepare_network``: `average_every_nhours() `_ and its `caller `_), In active use +``Co2L``, Add an overall absolute carbon-dioxide emissions limit configured in ``electricity: co2limit``. If a float is appended an overall emission limit relative to the emission level given in ``electricity: co2base`` is added (e.g. ``Co2L0.05`` limits emissisions to 5% of what is given in ``electricity: co2base``), ``prepare_network``: `add_co2limit() `_ and its `caller `_, In active use +``Ep``, Add cost for a carbon-dioxide price configured in ``costs: emission_prices: co2`` to ``marginal_cost`` of generators (other emission types listed in ``network.carriers`` possible as well), ``prepare_network``: `add_emission_prices() `_ and its `caller `_, In active use ``CCL``, Add minimum and maximum levels of generator nominal capacity per carrier for individual countries. These can be specified in the file linked at ``electricity: agg_p_nom_limits`` in the configuration. File defaults to ``data/agg_p_nom_minmax.csv``., ``solve_network``, In active use -``Ep``, Add cost for a carbon-dioxide price configured in ``costs: emission_prices: co2`` to ``marginal_cost`` of generators, ``prepare_network``: `add_emission_prices() `_ and its `caller `_, Broken ``BAU``, Add a per-``carrier`` minimal overall capacity; i.e. at least ``40GW`` of ``OCGT`` in Europe; configured in ``electricity: BAU_mincapacities``, ``solve_network``: `add_opts_constraints() `_, Untested ``SAFE``, Add a capacity reserve margin of a certain fraction above the peak demand to which renewable generators and storage do *not* contribute. Ignores network., ``solve_network`` `add_opts_constraints() `_, Untested diff --git a/scripts/add_electricity.py b/scripts/add_electricity.py index cd1a5a82..c6876a51 100644 --- a/scripts/add_electricity.py +++ b/scripts/add_electricity.py @@ -564,19 +564,6 @@ def estimate_renewable_capacities(n, tech_map=None): .transform(lambda s: normed(s) * tech_capacities.at[s.name]) .where(lambda s: s>0.1, 0.)) # only capacities above 100kW -def add_co2limit(n, Nyears=1.): - n.add("GlobalConstraint", "CO2Limit", - carrier_attribute="co2_emissions", sense="<=", - constant=snakemake.config['electricity']['co2limit'] * Nyears) - -def add_emission_prices(n, emission_prices=None, exclude_co2=False): - if emission_prices is None: - emission_prices = snakemake.config['costs']['emission_prices'] - if exclude_co2: emission_prices.pop('co2') - ep = (pd.Series(emission_prices).rename(lambda x: x+'_emissions') * n.carriers).sum(axis=1) - n.generators['marginal_cost'] += n.generators.carrier.map(ep) - n.storage_units['marginal_cost'] += n.storage_units.carrier.map(ep) - def add_nice_carrier_names(n): nice_names = pd.Series(snakemake.config['plotting']['nice_names']) n.carriers['nice_names'] = nice_names[n.carriers.index] diff --git a/scripts/prepare_network.py b/scripts/prepare_network.py index 96c53447..55372745 100644 --- a/scripts/prepare_network.py +++ b/scripts/prepare_network.py @@ -3,7 +3,7 @@ Prepare PyPSA network for solving according to :ref:`opts` and :ref:`ll`, such as - adding an annual **limit** of carbon-dioxide emissions, -- adding an exogenous **price** of carbon-dioxide emissions, +- adding an exogenous **price** of carbon-dioxide emissions (or other kinds), - setting an **N-1 security margin** factor for transmission line capacities, - specifying a limit on the **cost** of transmission expansion, - specifying a limit on the **volume** of transmission expansion, and @@ -78,12 +78,10 @@ def add_co2limit(n, Nyears=1., factor=None): constant=annual_emissions * Nyears) def add_emission_prices(n, emission_prices=None, exclude_co2=False): - assert False, "Needs to be fixed, adds NAN" - if emission_prices is None: emission_prices = snakemake.config['costs']['emission_prices'] if exclude_co2: emission_prices.pop('co2') - ep = (pd.Series(emission_prices).rename(lambda x: x+'_emissions') * n.carriers).sum(axis=1) + ep = (pd.Series(emission_prices).rename(lambda x: x+'_emissions') * n.carriers.filter(like='_emissions')).sum(axis=1) n.generators['marginal_cost'] += n.generators.carrier.map(ep) n.storage_units['marginal_cost'] += n.storage_units.carrier.map(ep) @@ -215,8 +213,8 @@ if __name__ == "__main__": else: add_co2limit(n, Nyears) - # if 'Ep' in opts: - # add_emission_prices(n) + if 'Ep' in opts: + add_emission_prices(n) ll_type, factor = snakemake.wildcards.ll[0], snakemake.wildcards.ll[1:] if ll_type == 'v':