121 lines
5.1 KiB
Python
121 lines
5.1 KiB
Python
import json
|
|
import gurobipy as gp
|
|
import pandas as pd
|
|
from gurobipy import GRB
|
|
|
|
|
|
data = pd.read_csv("data/data.csv")
|
|
price = data['price']
|
|
load = data['load']
|
|
pre_pv = data['pv']
|
|
wind = data['wind']
|
|
period = len(data)
|
|
|
|
DG_parameters = {
|
|
'gen_1': {'a': 0.0034, 'b': 3, 'c': 30,
|
|
'power_output_max': 150, 'power_output_min': 10,
|
|
'ramping_up': 100, 'ramping_down': 100},
|
|
|
|
'gen_2': {'a': 0.001, 'b': 10, 'c': 40,
|
|
'power_output_max': 375, 'power_output_min': 50,
|
|
'ramping_up': 100, 'ramping_down': 100},
|
|
|
|
'gen_3': {'a': 0.001, 'b': 15, 'c': 70,
|
|
'power_output_max': 500, 'power_output_min': 100,
|
|
'ramping_up': 200, 'ramping_down': 200}
|
|
}
|
|
|
|
|
|
def get_dg_info(parameters):
|
|
p_max = []
|
|
p_min = []
|
|
ramping_up = []
|
|
ramping_down = []
|
|
a_para = []
|
|
b_para = []
|
|
c_para = []
|
|
for name, gen_info in parameters.items():
|
|
p_max.append(gen_info['power_output_max'])
|
|
p_min.append(gen_info['power_output_min'])
|
|
ramping_up.append(gen_info['ramping_up'])
|
|
ramping_down.append(gen_info['ramping_down'])
|
|
a_para.append(gen_info['a'])
|
|
b_para.append(gen_info['b'])
|
|
c_para.append(gen_info['c'])
|
|
return p_max, p_min, ramping_up, ramping_down, a_para, b_para, c_para
|
|
|
|
|
|
p_max, p_min, ramping_up, ramping_down, a_para, b_para, c_para = get_dg_info(parameters=DG_parameters)
|
|
NUM_GEN = len(DG_parameters.keys())
|
|
grid_exchange_ability = 100
|
|
sell_coefficient = 0.5
|
|
battery_capacity = 500
|
|
battery_efficiency = 0.9
|
|
initial_soc = 0.2
|
|
battery_degradation = 0.01
|
|
battery_holding = 0.1
|
|
battery_maxcharge = 100
|
|
solar_cofficient = 0.01
|
|
wind_cofficient = 0.01
|
|
|
|
m = gp.Model("UC")
|
|
|
|
# 设置系统变量
|
|
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')
|
|
# 设置充放电约束
|
|
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=-battery_maxcharge, ub=battery_maxcharge, name='battery_action')
|
|
# 设置外部电网与能源系统交换约束
|
|
grid_energy_import = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0, ub=grid_exchange_ability, name='import')
|
|
grid_energy_export = m.addVars(period, vtype=GRB.CONTINUOUS, lb=0, ub=grid_exchange_ability, name='export')
|
|
# 设置电压控制约束
|
|
pv_voltage = m.addVars(period, vtype=GRB.CONTINUOUS, lb=-1, ub=1, name='pv_voltage')
|
|
|
|
# 计算光伏发电量
|
|
pv = [pre_pv[t] * (1 + pv_voltage[t]) for t in range(period)]
|
|
|
|
# 1. 添加平衡约束
|
|
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')
|
|
# 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)),
|
|
'gen_output_max')
|
|
m.addConstrs((gen_output[g, t] >= on_off[g, t] * p_min[g] for g in range(NUM_GEN) for t in range(period)),
|
|
'gen_output_min')
|
|
# 3. 添加上升和下降约束
|
|
m.addConstrs((gen_output[g, t + 1] - gen_output[g, t] <= ramping_up[g] for g in range(NUM_GEN)
|
|
for t in range(period - 1)), 'ramping_up')
|
|
m.addConstrs((gen_output[g, t] - gen_output[g, t + 1] <= ramping_down[g] for g in range(NUM_GEN)
|
|
for t in range(period - 1)), 'ramping_down')
|
|
# 4. 添加电池容量约束
|
|
m.addConstr(battery_capacity * soc[0] == battery_capacity * initial_soc +
|
|
(battery_energy_change[0] * battery_efficiency), name='soc0')
|
|
m.addConstrs((battery_capacity * soc[t] == battery_capacity * soc[t - 1] +
|
|
(battery_energy_change[t] * battery_efficiency) for t in range(1, period)), name='soc update')
|
|
# 设置成本函数
|
|
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 t in range(period) for g in range(NUM_GEN))
|
|
cost_battery = gp.quicksum(
|
|
battery_energy_change[t] * battery_degradation + soc[t] * battery_holding 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] * sell_coefficient 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))
|
|
|
|
m.setObjective((cost_gen + cost_battery + cost_import - cost_export + cost_solar + cost_wind), GRB.MINIMIZE)
|
|
m.optimize()
|
|
|
|
# 记录动作便于辅助决策
|
|
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_9.3.json', 'w') as f:
|
|
json.dump(results, f, indent=2)
|