wip bess swap time prediction
This commit is contained in:
parent
1b29cfdea8
commit
04cf0cdf29
@ -1,3 +1,6 @@
|
||||
import pandas as pd
|
||||
|
||||
|
||||
def initialise_SoC(bess):
|
||||
"""Initialise the state of charge (SoC) for the BESS."""
|
||||
for i in range(0, len(bess["units"])): # initially fully charged
|
||||
@ -7,13 +10,14 @@ def initialise_SoC(bess):
|
||||
|
||||
def initial_site_assignment(c, bess):
|
||||
"""Initialise the site assignment for each BESS."""
|
||||
k = 0
|
||||
while k < len(c["site_info"]["sites"]):
|
||||
bess["units"][k]["site"] = c["site_info"]["sites"][k]["name"]
|
||||
k += 1
|
||||
|
||||
if k < len(c["site_info"]["sites"]):
|
||||
bess["units"][k]["site"] = "Unassigned"
|
||||
for k in range(0, len(bess["units"])):
|
||||
# assign each BESS unit to a site
|
||||
if k < len(c["site_info"]["sites"]):
|
||||
bess["units"][k]["site"] = c["site_info"]["sites"][k]["name"]
|
||||
else:
|
||||
bess["units"][k]["site"] = "Unassigned"
|
||||
|
||||
return bess
|
||||
|
||||
|
||||
@ -23,10 +27,14 @@ def discharge_bess(bess, site_name, dt, discharge_power):
|
||||
|
||||
"""Discharge the BESS for a specific site."""
|
||||
for index, unit in enumerate(bess["units"]):
|
||||
if unit["site"] == "Unassigned":
|
||||
continue
|
||||
|
||||
if unit["site"] == site_name:
|
||||
new_soc = unit["SoC"] - (dt * discharge_energy) / unit["capacity_kWh"]
|
||||
new_soc = 0 if new_soc < 0 else new_soc
|
||||
else:
|
||||
# maintain SoC if not assigned to the site
|
||||
new_soc = unit["SoC"]
|
||||
|
||||
# update SoC
|
||||
@ -37,8 +45,49 @@ def discharge_bess(bess, site_name, dt, discharge_power):
|
||||
def predict_swap_time(bess_soc_for_cycle):
|
||||
"""Predict the swap time for each BESS unit based on its SoC history."""
|
||||
swap_times = {}
|
||||
min2sec = 60
|
||||
threshold = 2 * min2sec # 2 minutes in seconds
|
||||
|
||||
for unit_name, df in bess_soc_for_cycle.items():
|
||||
# Find the timestamp when SoC reaches 0
|
||||
swap_time = df[df["SoC"] == 0]["Timestamp"].min()
|
||||
# need to be at least 1 min of operation to start estimation
|
||||
if len(df) < threshold:
|
||||
swap_times[unit_name] = None
|
||||
continue
|
||||
|
||||
# linear extrapolation to estimate swap time
|
||||
# calculate the slope of the SoC over time
|
||||
m = (df["SoC"].iloc[-1] - df["SoC"].iloc[0]) / (
|
||||
df["Timestamp"].iloc[-1] - df["Timestamp"].iloc[0]
|
||||
)
|
||||
|
||||
if m == 0:
|
||||
swap_times[unit_name] = None
|
||||
continue
|
||||
|
||||
# solve for the time when SoC reaches 0
|
||||
swap_time = (0 - df["SoC"].iloc[0]) / m + df["Timestamp"].iloc[0]
|
||||
# assign to swap_times
|
||||
swap_times[unit_name] = swap_time
|
||||
|
||||
return swap_times
|
||||
|
||||
|
||||
def update_cycle_SoC(bess_data, bess_soc_for_cycle, timestamps):
|
||||
init_df = pd.DataFrame(columns=["Timestamp", "SoC"])
|
||||
# assign SoC for cycle
|
||||
for unit in bess_data["units"]:
|
||||
unit_name = unit["name"]
|
||||
# reset df if SoC is 0. Start a new cycle
|
||||
if unit["SoC"] == 0:
|
||||
bess_soc_for_cycle[unit_name] = init_df
|
||||
|
||||
bess_soc_for_cycle[unit_name] = pd.concat(
|
||||
[
|
||||
bess_soc_for_cycle[unit_name],
|
||||
pd.DataFrame(
|
||||
[[timestamps[i], unit["SoC"]]],
|
||||
columns=["Timestamp", "SoC"],
|
||||
),
|
||||
],
|
||||
axis=0,
|
||||
)
|
||||
|
||||
20
main.py
20
main.py
@ -7,6 +7,7 @@ from Utilities.BESS import (
|
||||
initial_site_assignment,
|
||||
discharge_bess,
|
||||
predict_swap_time,
|
||||
update_cycle_SoC,
|
||||
)
|
||||
import matplotlib.pyplot as pl
|
||||
import pandas as pd
|
||||
@ -95,22 +96,9 @@ with ThreadPoolExecutor() as executor:
|
||||
axis=0,
|
||||
)
|
||||
|
||||
# assign SoC for cycle
|
||||
for unit in bess_data["units"]:
|
||||
unit_name = unit["name"]
|
||||
# reset df if SoC is 0. Start a new cycle
|
||||
if unit["SoC"] == 0:
|
||||
bess_soc_for_cycle[unit_name] = init_df
|
||||
bess_soc_for_cycle[unit_name] = pd.concat(
|
||||
[
|
||||
bess_soc_for_cycle[unit_name],
|
||||
pd.DataFrame(
|
||||
[[timestamps[i], unit["SoC"]]],
|
||||
columns=["Timestamp", "SoC"],
|
||||
),
|
||||
],
|
||||
axis=0,
|
||||
)
|
||||
# update cycle SoC
|
||||
# this is for predicting swap times
|
||||
bess_soc_for_cycle = update_cycle_SoC(bess_data, bess_soc_for_cycle, timestamps)
|
||||
|
||||
# predict swap times
|
||||
swap_times = predict_swap_time(bess_soc_for_cycle)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user