修复了逻辑,优先弃光,当达到最大弃光比例后,再弃风。
This commit is contained in:
@@ -145,28 +145,11 @@ def calculate_energy_balance(
|
||||
# 设置初始储能状态
|
||||
storage_soc[0] = initial_soc
|
||||
|
||||
# 计算总发电潜力
|
||||
total_potential_wind = np.sum(wind)
|
||||
total_potential_solar = np.sum(solar)
|
||||
|
||||
# 判断是否只有一种可再生能源
|
||||
has_wind = total_potential_wind > 0
|
||||
has_solar = total_potential_solar > 0
|
||||
single_renewable = (has_wind and not has_solar) or (has_solar and not has_wind)
|
||||
|
||||
# 计算允许的最大弃风弃光量
|
||||
if single_renewable:
|
||||
# 只有一种可再生能源时,弃电量不受限制
|
||||
max_curtailed_wind_total = float('inf')
|
||||
max_curtailed_solar_total = float('inf')
|
||||
elif params.max_grid_ratio == 0:
|
||||
# 上网电量限制为0时,所有超额电力都必须被弃掉,不受弃风弃光限制
|
||||
max_curtailed_wind_total = float('inf')
|
||||
max_curtailed_solar_total = float('inf')
|
||||
else:
|
||||
# 有多种可再生能源且上网电量限制不为0时,应用弃风弃光限制
|
||||
max_curtailed_wind_total = total_potential_wind * params.max_curtailment_wind
|
||||
max_curtailed_solar_total = total_potential_solar * params.max_curtailment_solar
|
||||
# 新逻辑:弃光受最大弃光比例限制,弃风不受限制
|
||||
total_solar_potential = sum(solar_output)
|
||||
max_curtailed_solar_total = total_solar_potential * params.max_curtailment_solar
|
||||
max_curtailed_wind_total = float('inf') # 弃风不受限制
|
||||
|
||||
# 初始化累计弃风弃光量
|
||||
accumulated_curtailed_wind = 0.0
|
||||
@@ -224,55 +207,24 @@ def calculate_energy_balance(
|
||||
# 剩余电力考虑弃风弃光
|
||||
remaining_surplus -= grid_feed_allowed
|
||||
|
||||
# 计算弃风弃光(优先弃光,然后弃风)
|
||||
# 计算弃风弃光(新逻辑:先弃光,当达到最大弃光比例后,再弃风,弃风不限)
|
||||
if remaining_surplus > 0:
|
||||
# 在单一可再生能源场景下,弃风弃光不受限制
|
||||
if single_renewable:
|
||||
# 优先弃光
|
||||
if solar[hour] > 0:
|
||||
curtailed_solar[hour] = min(solar[hour], remaining_surplus)
|
||||
remaining_surplus -= curtailed_solar[hour]
|
||||
accumulated_curtailed_solar += curtailed_solar[hour]
|
||||
|
||||
# 如果还有剩余,弃风
|
||||
if remaining_surplus > 0 and wind[hour] > 0:
|
||||
curtailed_wind[hour] = min(wind[hour], remaining_surplus)
|
||||
remaining_surplus -= curtailed_wind[hour]
|
||||
accumulated_curtailed_wind += curtailed_wind[hour]
|
||||
else:
|
||||
# 混合可再生能源场景,弃风弃光受限制
|
||||
# 计算当前可弃光量
|
||||
if max_curtailed_solar_total == float('inf'):
|
||||
# 无限制弃光
|
||||
available_solar_curtail = solar[hour]
|
||||
else:
|
||||
# 受限制弃光
|
||||
available_solar_curtail = min(
|
||||
solar[hour],
|
||||
max_curtailed_solar_total - accumulated_curtailed_solar
|
||||
)
|
||||
|
||||
if available_solar_curtail > 0:
|
||||
curtailed_solar[hour] = min(available_solar_curtail, remaining_surplus)
|
||||
remaining_surplus -= curtailed_solar[hour]
|
||||
accumulated_curtailed_solar += curtailed_solar[hour]
|
||||
|
||||
# 如果还有剩余,弃风
|
||||
if remaining_surplus > 0:
|
||||
if max_curtailed_wind_total == float('inf'):
|
||||
# 无限制弃风
|
||||
available_wind_curtail = wind[hour]
|
||||
else:
|
||||
# 受限制弃风
|
||||
available_wind_curtail = min(
|
||||
wind[hour],
|
||||
max_curtailed_wind_total - accumulated_curtailed_wind
|
||||
)
|
||||
|
||||
if available_wind_curtail > 0:
|
||||
curtailed_wind[hour] = min(available_wind_curtail, remaining_surplus)
|
||||
remaining_surplus -= curtailed_wind[hour]
|
||||
accumulated_curtailed_wind += curtailed_wind[hour]
|
||||
# 计算当前还能弃光的量
|
||||
remaining_solar_curtailment_quota = max_curtailed_solar_total - accumulated_curtailed_solar
|
||||
|
||||
# 优先弃光,但不超过最大弃光比例
|
||||
if solar[hour] > 0 and remaining_solar_curtailment_quota > 0:
|
||||
# 可以弃光的量取:光伏出力、剩余盈余电力、剩余弃光配额的最小值
|
||||
curtailed_solar[hour] = min(solar[hour], remaining_surplus, remaining_solar_curtailment_quota)
|
||||
remaining_surplus -= curtailed_solar[hour]
|
||||
accumulated_curtailed_solar += curtailed_solar[hour]
|
||||
|
||||
# 如果还有剩余电力,弃风(弃风不限)
|
||||
if remaining_surplus > 0 and wind[hour] > 0:
|
||||
# 弃风不受限制,可以弃掉所有剩余风电
|
||||
curtailed_wind[hour] = min(wind[hour], remaining_surplus)
|
||||
remaining_surplus -= curtailed_wind[hour]
|
||||
accumulated_curtailed_wind += curtailed_wind[hour]
|
||||
|
||||
# 确保电力平衡:如果仍有剩余电力,强制弃掉(安全机制)
|
||||
if remaining_surplus > 0:
|
||||
@@ -408,6 +360,7 @@ def check_constraints(
|
||||
solar_output: 光伏出力曲线 (MW) - 支持24小时或8760小时
|
||||
wind_output: 风电出力曲线 (MW) - 支持24小时或8760小时
|
||||
thermal_output: 火电出力曲线 (MW) - 支持24小时或8760小时
|
||||
load_demand: 负荷曲线 (MW) - 支持24小时或8760小时
|
||||
balance_result: 电能平衡计算结果
|
||||
params: 系统参数配置
|
||||
|
||||
@@ -456,7 +409,6 @@ def optimize_storage_capacity(
|
||||
Args:
|
||||
solar_output: 光伏出力曲线 (MW) - 支持24小时或8760小时
|
||||
wind_output: 风电出力曲线 (MW) - 支持24小时或8760小时
|
||||
thermal_output: 火电出力曲线 (MW) - 支持24小时或8760小时
|
||||
load_demand: 负荷曲线 (MW) - 支持24小时或8760小时
|
||||
params: 系统参数配置
|
||||
max_iterations: 最大迭代次数
|
||||
@@ -526,19 +478,22 @@ def optimize_storage_capacity(
|
||||
grid_constraint_satisfied = constraint_results['total_grid_feed_in_ratio'] <= params.max_grid_ratio
|
||||
else:
|
||||
grid_constraint_satisfied = True
|
||||
|
||||
# 新逻辑:弃光受最大弃光比例限制,弃风不受限制
|
||||
solar_constraint_satisfied = constraint_results['total_curtailment_solar_ratio'] <= params.max_curtailment_solar
|
||||
# 弃风不受限制,始终满足
|
||||
wind_constraint_satisfied = True
|
||||
|
||||
# 考虑浮点数误差,判断上网电量比例是否为0
|
||||
grid_quota_zero = abs(params.max_grid_ratio) < 1e-10
|
||||
|
||||
has_wind = sum(wind_output) > 0
|
||||
has_solar = sum(solar_output) > 0
|
||||
single_renewable = (has_wind and not has_solar) or (has_solar and not has_wind)
|
||||
grid_quota_zero = params.max_grid_ratio == 0
|
||||
|
||||
if single_renewable or grid_quota_zero:
|
||||
constraints_satisfied = grid_constraint_satisfied
|
||||
if grid_quota_zero:
|
||||
constraints_satisfied = grid_constraint_satisfied and solar_constraint_satisfied
|
||||
else:
|
||||
constraints_satisfied = (
|
||||
constraint_results['total_curtailment_wind_ratio'] <= params.max_curtailment_wind and
|
||||
constraint_results['total_curtailment_solar_ratio'] <= params.max_curtailment_solar and
|
||||
grid_constraint_satisfied
|
||||
solar_constraint_satisfied and # 弃光受限制
|
||||
wind_constraint_satisfied and # 弃风不受限制
|
||||
grid_constraint_satisfied # 上网电量受限制
|
||||
)
|
||||
|
||||
# 检查储能日平衡(周期结束时储能状态应接近初始值)
|
||||
@@ -766,4 +721,4 @@ def main():
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
main()
|
||||
|
||||
Reference in New Issue
Block a user