update battery cost

This commit is contained in:
chenxiaodong 2024-07-09 10:47:10 +08:00
parent 82ccfa7076
commit ed51c79123
1 changed files with 40 additions and 15 deletions

View File

@ -4,6 +4,7 @@ import numpy as np
import numpy.random as rd import numpy.random as rd
import pandas as pd import pandas as pd
import torch import torch
import json
from gurobipy import GRB from gurobipy import GRB
@ -14,9 +15,6 @@ def optimization_base_result(env, month, day, initial_soc):
irradiance = env.data_manager.get_series_irradiance_data(month, day) irradiance = env.data_manager.get_series_irradiance_data(month, day)
wind_speed = env.data_manager.get_series_wind_data(month, day) wind_speed = env.data_manager.get_series_wind_data(month, day)
pv = [env.solar.step(temp, irr) for temp, irr in zip(temperature, irradiance)]
wind = [env.wind.step(ws) for ws in wind_speed]
period = env.episode_length period = env.episode_length
DG_parameters = env.dg_parameters DG_parameters = env.dg_parameters
@ -28,7 +26,6 @@ def optimization_base_result(env, month, day, initial_soc):
a_para = [] a_para = []
b_para = [] b_para = []
c_para = [] c_para = []
for name, gen_info in parameters.items(): for name, gen_info in parameters.items():
p_max.append(gen_info['power_output_max']) p_max.append(gen_info['power_output_max'])
p_min.append(gen_info['power_output_min']) p_min.append(gen_info['power_output_min'])
@ -44,7 +41,10 @@ def optimization_base_result(env, month, day, initial_soc):
battery_capacity = env.battery.capacity battery_capacity = env.battery.capacity
battery_efficiency = env.battery.efficiency battery_efficiency = env.battery.efficiency
solar_cofficient = env.solar.opex_cofficient solar_cofficient = env.solar.opex_cofficient
volatage_change_percent = env.solar.change_percent
wind_cofficient = env.wind.opex_cofficient wind_cofficient = env.wind.opex_cofficient
battery_degradation = env.battery.degradation
battery_holding = env.battery.holding
m = gp.Model("UC") m = gp.Model("UC")
@ -52,16 +52,24 @@ def optimization_base_result(env, month, day, initial_soc):
on_off = m.addVars(NUM_GEN, period, vtype=GRB.BINARY, name='on_off') on_off = m.addVars(NUM_GEN, period, vtype=GRB.BINARY, name='on_off')
gen_output = m.addVars(NUM_GEN, period, vtype=GRB.CONTINUOUS, name='output') gen_output = m.addVars(NUM_GEN, period, vtype=GRB.CONTINUOUS, name='output')
# 设置充放电约束 # 设置充放电约束
soc = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0.2, ub=0.8, name='SOC')
battery_energy_change = m.addVars(period, vtype=GRB.CONTINUOUS, lb=-env.battery.max_charge, battery_energy_change = m.addVars(period, vtype=GRB.CONTINUOUS, lb=-env.battery.max_charge,
ub=env.battery.max_charge, name='battery_action') ub=env.battery.max_charge, name='battery_action')
# 设置外部电网与能源系统交换约束 # 设置外部电网与能源系统交换约束
grid_energy_import = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0, ub=env.grid.exchange_ability, name='import') grid_energy_import = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0, ub=env.grid.exchange_ability, name='import')
grid_energy_export = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0, ub=env.grid.exchange_ability, name='export') grid_energy_export = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0, ub=env.grid.exchange_ability, name='export')
soc = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0.2, ub=0.8, name='SOC') # 设置电压控制约束
pv_voltage = m.addVars(period, vtype=GRB.CONTINUOUS, lb=-1, ub=1, name='pv_voltage')
# 计算光伏和风力发电量
pv = [(0.2 * irradiance[t] + 0.05 * temperature[t] - 9.25) *
(1 + volatage_change_percent * pv_voltage[t]) for t in range(period)]
wind = [172.265625 * wind_speed[t] ** 3 / 1e3 if 3 <= wind_speed[t] < 8
else (172.265625 * 8 ** 3 / 1e3 if 8 <= wind_speed[t] < 12 else 0) for t in range(period)]
# 1. 添加平衡约束 # 1. 添加平衡约束
m.addConstrs(((sum(gen_output[g, t] for g in range(NUM_GEN)) + pv[t] + wind[t] + grid_energy_import[t] >= load[t] + m.addConstrs(((sum(gen_output[g, t] for g in range(NUM_GEN)) + pv[t] + wind[t] + grid_energy_import[t] >= load[t]
battery_energy_change[t] + grid_energy_export[t]) for t in range(period)), name='powerbalance') + battery_energy_change[t] + grid_energy_export[t]) for t in range(period)), name='powerbalance')
# 2. 添加发电机最大/最小功率约束 # 2. 添加发电机最大/最小功率约束
m.addConstrs((gen_output[g, t] <= on_off[g, t] * p_max[g] for g in range(NUM_GEN) for t in range(period)), m.addConstrs((gen_output[g, t] <= on_off[g, t] * p_max[g] for g in range(NUM_GEN) for t in range(period)),
'gen_output_max') 'gen_output_max')
@ -81,14 +89,18 @@ def optimization_base_result(env, month, day, initial_soc):
cost_gen = gp.quicksum( cost_gen = gp.quicksum(
(a_para[g] * gen_output[g, t] * gen_output[g, t] + b_para[g] * gen_output[g, t] + c_para[g] * on_off[g, t]) for (a_para[g] * gen_output[g, t] * gen_output[g, t] + b_para[g] * gen_output[g, t] + c_para[g] * on_off[g, t]) for
t in range(period) for g in range(NUM_GEN)) t in range(period) for g in range(NUM_GEN))
cost_grid_import = gp.quicksum(grid_energy_import[t] * price[t] for t in range(period)) cost_battery = gp.quicksum(battery_energy_change[t] * battery_degradation + soc[t] * battery_holding for t in range(period))
cost_grid_export = gp.quicksum(grid_energy_export[t] * price[t] * env.sell_coefficient for t in range(period)) cost_import = gp.quicksum(grid_energy_import[t] * price[t] for t in range(period))
cost_export = gp.quicksum(grid_energy_export[t] * price[t] * env.sell_coefficient for t in range(period))
cost_solar = gp.quicksum(pv[t] * solar_cofficient for t in range(period)) cost_solar = gp.quicksum(pv[t] * solar_cofficient for t in range(period))
cost_wind = gp.quicksum(wind[t] * wind_cofficient for t in range(period)) cost_wind = gp.quicksum(wind[t] * wind_cofficient for t in range(period))
m.setObjective((cost_gen + cost_grid_import - cost_grid_export + cost_solar + cost_wind), GRB.MINIMIZE) m.setObjective((cost_gen + cost_battery + cost_import - cost_export + cost_solar + cost_wind), GRB.MINIMIZE)
m.optimize() m.optimize()
# 记录数据便于绘图
pv = [(0.2 * irradiance[t] + 0.05 * temperature[t] - 9.25) *
(1 + volatage_change_percent * pv_voltage[t].x) for t in range(period)]
output_record = {'pv': [], 'wind': [], 'price': [], 'load': [], 'netload': [], output_record = {'pv': [], 'wind': [], 'price': [], 'load': [], 'netload': [],
'soc': [], 'battery_energy_change': [], 'grid_import': [], 'grid_export': [], 'soc': [], 'battery_energy_change': [], 'grid_import': [], 'grid_export': [],
'gen1': [], 'gen2': [], 'gen3': [], 'step_cost': []} 'gen1': [], 'gen2': [], 'gen3': [], 'step_cost': []}
@ -96,8 +108,9 @@ def optimization_base_result(env, month, day, initial_soc):
gen_cost = sum((on_off[g, t].x * ( gen_cost = sum((on_off[g, t].x * (
a_para[g] * gen_output[g, t].x * gen_output[g, t].x + b_para[g] * gen_output[g, t].x + c_para[g])) a_para[g] * gen_output[g, t].x * gen_output[g, t].x + b_para[g] * gen_output[g, t].x + c_para[g]))
for g in range(NUM_GEN)) for g in range(NUM_GEN))
grid_import_cost = grid_energy_import[t].x * price[t] battery_cost = battery_energy_change[t].x * battery_degradation + soc[t].x * battery_holding
grid_export_cost = grid_energy_export[t].x * price[t] * env.sell_coefficient import_cost = grid_energy_import[t].x * price[t]
export_cost = grid_energy_export[t].x * price[t] * env.sell_coefficient
solar_cost = pv[t] * solar_cofficient solar_cost = pv[t] * solar_cofficient
wind_cost = wind[t] * wind_cofficient wind_cost = wind[t] * wind_cofficient
output_record['pv'].append(pv[t]) output_record['pv'].append(pv[t])
@ -112,7 +125,18 @@ def optimization_base_result(env, month, day, initial_soc):
output_record['gen1'].append(gen_output[0, t].x) output_record['gen1'].append(gen_output[0, t].x)
output_record['gen2'].append(gen_output[1, t].x) output_record['gen2'].append(gen_output[1, t].x)
output_record['gen3'].append(gen_output[2, t].x) output_record['gen3'].append(gen_output[2, t].x)
output_record['step_cost'].append(gen_cost + grid_import_cost - grid_export_cost + solar_cost + wind_cost) output_record['step_cost'].append(gen_cost + battery_cost + import_cost - export_cost + solar_cost + wind_cost)
# 记录动作便于辅助决策
results = []
for t in range(period):
action = [battery_energy_change[t].x/100, (gen_output[0, t].x - (gen_output[0, t-1].x if t > 0 else 0))/100,
(gen_output[1, t].x - (gen_output[1, t-1].x if t > 0 else 0))/100,
(gen_output[2, t].x - (gen_output[2, t-1].x if t > 0 else 0))/200,
pv_voltage[t].x - (pv_voltage[t-1].x if t > 0 else 0)]
results.append(action)
with open('./results.json', 'w') as f:
json.dump(results, f, indent=2)
output_record_df = pd.DataFrame.from_dict(output_record) output_record_df = pd.DataFrame.from_dict(output_record)
return output_record_df return output_record_df
@ -184,7 +208,7 @@ def test_one_episode(env, act, device):
record_output = [] record_output = []
record_cost = [] record_cost = []
record_unbalance = [] record_unbalance = []
record_system_info = [] # [time price,netload,action,real action, output*4,soc,unbalance(exchange+penalty)] record_system_info = [] # [time,price,netload,action,real action,soc,output*4,unbalance(exchange+penalty),cost]
record_init_info = [] # include month,day,time,intial soc record_init_info = [] # include month,day,time,intial soc
env.TRAIN = False env.TRAIN = False
state = env.reset() state = env.reset()
@ -207,7 +231,8 @@ def test_one_episode(env, act, device):
record_unbalance.append(env.unbalance) record_unbalance.append(env.unbalance)
state = next_state state = next_state
# add information of last step dg1, dh2, dg3, soc # add information of last step dg1, dh2, dg3, soc
record_system_info[-1][7:10] = [env.final_step_outputs[0], env.final_step_outputs[1], env.final_step_outputs[2]] record_system_info[-1][7:12] = [env.final_step_outputs[0], env.final_step_outputs[1], env.final_step_outputs[2],
env.final_step_outputs[4], env.final_step_outputs[5]]
record_system_info[-1][5] = env.final_step_outputs[3] record_system_info[-1][5] = env.final_step_outputs[3]
record = {'init_info': record_init_info, 'system_info': record_system_info, 'state': record_state, record = {'init_info': record_init_info, 'system_info': record_system_info, 'state': record_state,
'action': record_action, 'reward': record_reward, 'cost': record_cost, 'unbalance': record_unbalance, 'action': record_action, 'reward': record_reward, 'cost': record_cost, 'unbalance': record_unbalance,