第二届世界科学智能大赛社会科学赛道:市场博弈和价格预测学习心得

target

根据electricity price.csv(其中包括:电力市场的市场出清价格,市场需求等信息),unit.csv(存放市场供给者(各发电机组)的参数信息)两个文件,对electricity price.csv剩下的时长出清价格进行预测。

electricity price.csv:文件中包括以下几种数据:

  1. Day/Time:交易时间,中国电力现货市场15分钟结算一次,一天共96个交易点

  2. demand:区域内电力总负荷(总需求),单位为MW

  3. clearing price (CNY/MWh):市场出清电价,单位为元/MW·h

daytimedemandclearing price (CNY/MWh)
2021/12/10:1540334.18350.8
2021/12/10:3040523.15350.8
2021/12/10:4540374.74350.8

unit.csv:存放市场供给者(各发电机组)的参数信息,包括:

  1. unit ID:每个机组唯一的ID

  2. Capacity(MW):机组的额定容量(额定功率),越高机组的发电能力越强

  3. utilization hour (h) :电厂的年平均运行小时数,需要注意多个机组可能共同属于一个电厂,有相同的值

  4. coal consumption (g coal/KWh):每发一度电需要耗费多少煤炭,为成本参数

  5. power consumption rate:电厂单位时间内耗电量与发电量的百分比,例如单位时间耗电量为500度电,发电量为10000度电,利用率就是500/10000=5%。

unit IDCapacity (MW)Utilization Hour (h)Coal Consumption (g coal/KWh)Power Consumption Rate (%)
11102069.12266.076.91
21605509.22292.76.91
31603562.79293.356.91

Evaluation

 最终评价指标为MSE(均方误差)和RMSE(均方根误差)的均值(事实上这和只用RMSE或者MSE是一样的),值越小越好,公式如下:

\text{MSE}=\frac{\sum_{i=1}^{n} (y_i - \hat{y}_i)^2}{n}

\text{Final Metric}=\frac{\text{MSE}+\sqrt{\text{MSE}}}{2 }

其中:

  • y_i为真实市场出清价格

  • \hat y_i为预测的市场出清价格

  • n为样本数量,这里是测试集的大小28228

Method

 剥离题目的描述背景,我们可以将问题抽象为一个回归问题,即已知2021年12月1日-2023年7月1日的出清价格,需要对2023年7月1日-2024年4月18日的出清价格进行预测。可以首先使用表格中的各个变量与出清价格进行相关性检测,之后挑选合适的变量构造回归方程,即可解决问题。

同样可以使用人工智能的方法,构造多层的神经网络结构,对出清价格进行预测。

总而言之,纯粹依靠构造时间序列模型可以完成这个任务。

使用ABM(Agent-Based-Modeling)解决该问题的方法

首先介绍一个概念即边际成本:生产额外一单位产品(这里是一度电)带来的成本增加

出清价格是如何形成的呢?

  1. 所有发电机组申报自己卖出的电价和电量

  2. 市场根据机组报价,从低到高排序,依次从低价开始成交

  3. 当成交的容量和大于等于总需求时,达到市场出清(供需平衡),这时候最后一个达成交易的机组报价为市场出清价格

从上述过程来看,每一个机组都希望自己的报价都近似于最终的出清价格。如果报价高于出清价格,那么竞标失败,没有卖出任何电力。如果低于竞标价格,那么就少赚钱甚至亏本了。

但是,各个机组间存在竞争关系,各个机组并不清楚其他机组的报价。 为了保证自己的电力可以卖出去,并且不亏本。我们可以认为机组的报价为额外生产一度电带来的成本增加,即报价>=边际成本(当然实际情况并非如此)

最终的出清价格就是边际成本的最大值。因此,问题就转化为边际成本的最大值是多少。

下面从代码出发,解决问题:

1.导入库

import numpy as np
import pandas as pd
from pathlib import Path
from sklearn.linear_model import LinearRegression

2.数据预处理

由于最终提交的数据格式为:日期,时间,出清价格。因此删去demand列并保留未知出清价格的日期。

base_path = Path("data")  # 确保数据都放在同级的data目录下

# 读取市场数据
electricity_price = pd.read_csv(base_path / "electricity price.csv")
# 读取市场主体(各发电机组)数据
unit = pd.read_csv(base_path / "unit.csv")

"""
准备示例提交数据sample_submit
1. electricity_price["clearing price (CNY/MWh)"].isna()找到出清价格为缺失值的行,即要预测的目标
2. 去除demand列,符合最后的提交格式 
"""

sample_submit = electricity_price[electricity_price["clearing price (CNY/MWh)"].isna()].drop(columns="demand")
sample_submit.to_csv(base_path / "sample_submit.csv", index=False)

将日期和时间列合并为时间戳列。需要对24:00:00的情况特判。pandas无法处理24:00:00的情况。具体做法即将24:00:00字符串替换为00:00:00,同时日期+1

# 将day和time列合并成timestamp列,便于提取时间戳特征
electricity_price["timestamp"] = pd.to_datetime(
    electricity_price["day"] + " " + electricity_price["time"].str.replace("24:00:00", "00:00"))

# 处理24:00:00的情况,即表示第二天的00:00:00
mask = electricity_price['timestamp'].dt.time == pd.Timestamp('00:00:00').time()

# 需要将这些行的日期部分加一天
electricity_price.loc[mask, 'timestamp'] += pd.Timedelta(days=1)

# 设置列的顺序,同时去除day和time列
electricity_price = electricity_price[["timestamp", "demand", "clearing price (CNY/MWh)"]]

  • 4
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值