栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Python

简单 风功率预测模型

Python 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

简单 风功率预测模型



from time import time
import matplotlib.pyplot as plt
from sklearn.preprocessing import MinMaxScaler
import numpy as np
import tushare as ts
import torch
from torch import nn
from torch.optim import lr_scheduler
from tensorboardX import SummaryWriter
import pandas as pd
import set
import pymysql
from pyecharts.charts import Line
from pyecharts import options as opts

start= time()

TABLE_NAME = set.TABLE_NAME
# 是否打印sql
SHOW_SQL = set.SHOW_SQL
config = set.CONFIG
conn = pymysql.connect(**config)

df = pd.read_sql("select * from winderturbine_power_per_day where wt_date >'2018/1/1'",conn)
wind_speed=df.mean_wind_speed
# 清理数据 消除风速数据小于0的记录  给成平均值
wind_speed[wind_speed<=0]=5
df.mean_wind_speed=wind_speed

wind_speed= df.groupby('wt_date').mean_wind_speed.mean()

g= df.groupby('wt_date').active_power_generation.sum()

writer = SummaryWriter()
DAYS_FOR_TRAIN = 10
EPOCHS = 200
learning_rate=0.1
min_learning_rate=2e-5
HS=8 #hidden_siz
NL=2 #num_layers


class LSTM_Regression(nn.Module):
    """
        使用LSTM进行回归
        参数:
        - input_size: feature size
        - hidden_size: number of hidden units
        - output_size: number of output
        - num_layers: layers of LSTM to stack
    """

    def __init__(self, input_size, hidden_size, output_size=1, num_layers=2):#10 8 1 3
        super().__init__()
        self.lstm = nn.LSTM(input_size, hidden_size, num_layers)
        self.fc = nn.Linear(hidden_size, output_size)

    def forward(self, _x):
        x, _ = self.lstm(_x)  # _x is input, size (seq_len, batch, input_size)
        s, b, h = x.shape  # x is output, size (seq_len, batch, hidden_size)
        x = x.view(s * b, h)
        x = self.fc(x)
        x = x.view(s, b, -1)  # 把形状改回来
        return x


def create_dataset(data, days_for_train=5) -> (np.array, np.array):
    """
        根据给定的序列data,生成数据集。
        数据集分为输入和输出,每一个输入的长度为days_for_train,每一个输出的长度为1。
        也就是说用days_for_train天的数据,对应下一天的数据。
        若给定序列的长度为d,将输出长度为(d-days_for_train)个输入/输出对
        根据10天数据预测第11天数据  
    """
    dataset_x, dataset_y = [], []
    for i in range(len(data) - days_for_train):
        _x = data[i:(i + days_for_train)]
        dataset_x.append(_x)
        dataset_y.append(data[i + days_for_train])
    return (np.array(dataset_x), np.array(dataset_y))




if __name__ == '__main__':

    share_prices=np.array(wind_speed).astype('float32')

    # 上证指数收盘价作图
    plt.plot(share_prices)
    plt.savefig('share_prices.png', format='png', dpi=200)
    plt.close()
    # 将数据集标准化到 [-1,1] 区间
    scaler = MinMaxScaler(feature_range=(0, 1))  # train data normalized
    share_prices = scaler.fit_transform(share_prices.reshape(-1, 1))
    # 数据集序列化,进行标签分离
    dataset_x, dataset_y = create_dataset(share_prices, DAYS_FOR_TRAIN)
    # 划分训练集和测试集,70%作为训练集,30%作为测试集   
    train_size = int(len(dataset_x) * 0.90)
    train_x = dataset_x[:train_size]
    train_y = dataset_y[:train_size]
    test_x = dataset_x[train_size:]
    test_y = dataset_y[train_size:]
    # 改变数据集形状,RNN 读入的数据维度是 (seq_size, batch_size, feature_size)
    train_x = train_x.reshape(-1, 1, DAYS_FOR_TRAIN)
    train_y = train_y.reshape(-1, 1, 1)
    # 数据集转为pytorch的tensor对象
    train_x = torch.from_numpy(train_x)
    train_y = torch.from_numpy(train_y)
    # 训练模型
    model = LSTM_Regression(DAYS_FOR_TRAIN, hidden_size=HS, output_size=1, num_layers=NL)  # 网络初始化
    loss_function = nn.MSELoss()  # 损失函数
    optimizer = torch.optim.Adam(model.parameters(), lr=learning_rate)  # 优化器
    # 可调学习率
    lr_lambda = lambda epoch: max(0.54 ** (epoch//150),min_learning_rate)  # 函数2、.
    lr_list = []
    scheduler = lr_scheduler.LambdaLR(optimizer,lr_lambda=lr_lambda) 
    # scheduler = lr_scheduler.ReduceLROnPlateau(optimizer, mode='min', factor=0.1, patience=10, verbose=False, threshold=0.0001, threshold_mode='rel', cooldown=0, min_lr=0, eps=1e-08)
    
    for epoch in range(EPOCHS):
        scheduler.step()  # 学习率更新
        lr_list.append(optimizer.state_dict()['param_groups'][0]['lr']) # 可调学习率
        
        out = model(train_x)
        loss = loss_function(out, train_y)
        loss.backward()
        optimizer.step()
        optimizer.zero_grad()   
        writer.add_scalar('data/loss', loss, epoch)
        writer.add_scalar('data/lr', lr_list[-1], epoch)
        if (epoch + 1) % 20 == 0:
            print('{}{}Epoch: {}, Loss:{:.5f}'.format(HS,NL,epoch + 1, loss.item()))
            
            if loss.item() < 0.011:
                torch.save(model.state_dict(), './model/model_params_wind_speed'+
                   '{}{}_Epoch_{}, Loss_{:.5f},DFT{}'.format(HS,NL,epoch + 1, loss.item(),DAYS_FOR_TRAIN)+'.pkl')  # 可以保存模型的参数供未来使用

    torch.save(model.state_dict(), './model/model_params_wind_speed'+
                   '{}{}_Epoch_{}, Loss_{:.5f},DFT{}'.format(HS,NL,epoch + 1, loss.item(),DAYS_FOR_TRAIN)+'.pkl')  # 可以保存模型的参数供未来使用


    # predict 预测
    model = model.eval()  # 转换成测试模式
    #读取模型
    # model.load_state_dict(torch.load('./model/model_params_wind_speed93_Epoch_3000, Loss_0.01684,DFT18.pkl'))  # 读取参数
    # 使用全部数据集dataset_x,模型的输出长度会比dataset_x少 DAYS_FOR_TRAIN
    dataset_x = dataset_x.reshape(-1, 1, DAYS_FOR_TRAIN)  # (seq_size, batch_size, feature_size) 
    dataset_x = torch.from_numpy(dataset_x)  # 转为pytorch的tensor对象
    pred_y = model(dataset_x)  # 全量数据集的模型输出 (seq_size, batch_size, output_size)
    pred_y = pred_y.view(-1).data.numpy()
    # 画图
    with SummaryWriter(comment='LeNet{}{}'.format(HS,NL)) as w:
        w.add_graph(model, (dataset_x, ))
    # 对标准化数据进行还原
    actual_pred_y = scaler.inverse_transform(pred_y.reshape(-1, 1))
    actual_pred_y = actual_pred_y.reshape(-1, 1).flatten()
    test_y = scaler.inverse_transform(test_y.reshape(-1, 1))
    test_y = test_y.reshape(-1, 1).flatten()
    actual_pred_y = actual_pred_y[-len(test_y):]
    test_y = test_y.reshape(-1, 1)
    assert len(actual_pred_y) == len(test_y)
    writer.export_scalars_to_json("./test.json")
    writer.close()

    # 初始结果 - 预测结果
    plt.plot(actual_pred_y, 'r', label='prediction{}{}_Epoch_{}, Loss_{:.5f},DFT{}'.format(HS,NL,epoch + 1, loss.item(),DAYS_FOR_TRAIN))
    plt.plot(test_y, 'b', label='real')
    plt.plot((len(actual_pred_y), len(test_y)), (0, 1), 'g--')  # 分割线 左边是训练数据 右边是测试数据的输出
    plt.legend(loc='best')
    plt.savefig('./img/result{}{}_Epoch_{}, Loss_{:.5f},DFT{}'.format(HS,NL,epoch + 1, loss.item(),DAYS_FOR_TRAIN)+'.png', format='png', dpi=1200)
    plt.show()
    plt.close()
    end=time()
    print('运行: %.2f 秒'%(end-start))

    

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/943039.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号