Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Scripts needed to reproduce results in the NE/RE report #210

Merged
merged 5 commits into from
Jul 24, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions dispatches/case_studies/nuclear_case/report/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Source Code for Generating Nuclear Case Study Results in Report

This folder contains the source code used to generate the results shown in the combined report for nuclear and renewable case studies.

### `base_case_pcm_simulation.py`
This script performs a Prescient simulation of the base case i.e., nuclear generator without an electrolyzer. The script creates a new folder called `ne_without_pem_results` and saves the simulation results in that folder. Then, the LMP data at the bus `Attlee` is extracted from the file `bus_detail.csv`. For convenience, the extracted LMP data is included in the file `rts_gmlc_15_500.csv` file. This LMP data is used for the price-taker analysis.

### `traditional_tea.py`

This script performs the traditional techno-economic analysis. The function `run_exhaustive_enumeration` fixes the capacity of the electrolyzer and the selling price of hydrogen and computes the revenue from both electricity, and hydrogen markets and the annualized net present value. The script saves the results in a `json` file.

### `price_taker.py`

This script performs price-taker analysis. The function `run_exhaustive_enumeration` fixes the capacity of the electrolyzer and the selling price of hydrogen and computes the revenue from both electricity and hydrogen markets, and the annualized net present value. `market` argument to the function indicates which of the four price-taker variants to use for the analysis. To use the first variant (refer to the report for more details), specify `market="DA"`. For second, third, and fourth variants, specify `market="RT"`, `market="Max-DA-RT"`, and `market="DA-RT"`, respectively. The script saves the results in a `json` file.

### `market_surrogates.py`

Solves the conceptual design problem by embedding the surrogate models for market interactions. To run this script, `tensorflow` must be installed in the current environment. If it is not installed, the user can do so by running `pip install tensorflow` in a command window. The trained neural network surrogate models are included in the folder `nn_steady_state`. The function `run_exhaustive_enumeration` fixes the capacity of the electrolyzer and the selling price of hydrogen and computes the revenue from both electricity, and hydrogen markets and the annualized net present value, and saves the results in a `json` file.

### `generate_contour_plots.py`
This script generates the contour plots shown in the report.
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
#################################################################################
# DISPATCHES was produced under the DOE Design Integration and Synthesis Platform
# to Advance Tightly Coupled Hybrid Energy Systems program (DISPATCHES), and is
# copyright (c) 2020-2023 by the software owners: The Regents of the University
# of California, through Lawrence Berkeley National Laboratory, National
# Technology & Engineering Solutions of Sandia, LLC, Alliance for Sustainable
# Energy, LLC, Battelle Energy Alliance, LLC, University of Notre Dame du Lac, et
# al. All rights reserved.
#
# Please see the files COPYRIGHT.md and LICENSE.md for full copyright and license
# information, respectively. Both files are also available online at the URL:
# "https://github.com/gmlc-dispatches/dispatches".
#################################################################################

import os
from prescient.simulator import Prescient


def download_rts_gmlc(dir_name="DISPATCHES_RTS-GMLC"):
cur_path = os.getcwd()
this_file_path = os.path.dirname(os.path.realpath(__file__))

if os.path.isdir(os.path.join(this_file_path, dir_name)):
return

os.chdir(this_file_path)
os.system(f"git clone --depth=1 https://github.com/bknueven/RTS-GMLC -b no_reserves {dir_name}")

os.chdir(cur_path)


download_rts_gmlc()
this_file_path = os.path.dirname(os.path.realpath(__file__))

start_date = "01-01-2020"
n_days = 366
shortfall = 500 # 500 $/MWh
reserve_factor = 0.15 # 15% reserves
day_ahead_horizon = 36
real_time_horizon = 1
tracking_horizon = 4
n_tracking_hour = 1
output_dir = "ne_without_pem_results"

# default some options
prescient_options = {
"data_path": os.path.join(this_file_path, "DISPATCHES_RTS-GMLC/RTS_Data/SourceData"),
"reserve_factor": reserve_factor,
"simulate_out_of_sample": True,
"output_directory": output_dir,
"monitor_all_contingencies": False,
"input_format": "rts-gmlc",
"start_date": start_date,
"num_days": n_days,
"sced_horizon": real_time_horizon,
"ruc_mipgap": 0.01,
"deterministic_ruc_solver": "gurobi_persistent",
"deterministic_ruc_solver_options" : {
"threads": 4,
"heurstrategy": 2,
"cutstrategy": 3,
"symmetry": 2,
"maxnode": 1000,
},
"sced_solver": "gurobi_persistent",
"sced_frequency_minutes": 60,
"sced_solver_options" : {"threads": 1},
"ruc_horizon": day_ahead_horizon,
"compute_market_settlements": True,
"output_solver_logs": False,
"price_threshold": shortfall,
"transmission_price_threshold": shortfall / 2,
"contingency_price_threshold": None,
"reserve_price_threshold": shortfall / 10,
"day_ahead_pricing": "aCHP",
"enforce_sced_shutdown_ramprate": False,
"ruc_slack_type": "ref-bus-and-branches",
"sced_slack_type": "ref-bus-and-branches",
"disable_stackgraphs": True,
}


Prescient().simulate(**prescient_options)
Loading