解决多时序并列的预测问题的神经网络或机器学习模型

建立一个预测并列时间序列的神经网络模型

问题描述:现在系统有10个输入5个输出,输入参数相互独立,对5个输出有协同影响。10个输入能组合出n种工况。

解决问题:只有其中一部分工况的数据(所有工况均可实验,若有必需的数据可以继续实验获得),该如何训练一个模型,可以对所有组合出的工况都进行预测?

遇到困难:目前只会使用一组工况的数据训练模型,然后预测这一种工况。不能实现一个模型对系统全部工况进行预测。

可以借鉴下

import pandas as pd
 
import torch
import torch.nn as nn
from torch.utils.data import Dataset, DataLoader
import torch.optim as optim
 
import pandas as pd
import numpy as np
import lightgbm as lgb
from sklearn.metrics import mean_squared_error
 
df = pd.read_csv('Raotbl6.csv')
df['date'] = pd.to_datetime(df['date'])
df.index = df['date']
df.drop('date', axis=1, inplace=True)
 
# make future targets
for i in range(12):
    df['rgnp_{}'.format(i)] = df['rgnp'].shift(-i-1)
 
df.dropna(inplace=True)
 
targets = [item for item in df.columns if 'rgnp_' in item]
 
X_train = df.drop(targets, axis=1)[: int(len(df) * 0.8)]
y_train = df[targets][: int(len(df) * 0.8)]
 
X_test = df.drop(targets, axis=1)[int(len(df) * 0.8) :]
y_test = df[targets][int(len(df) * 0.8) :]

可以考虑使用多任务学习模型来训练您的神经网络模型。多任务学习将多个相关任务视为一个问题,通过共享底层模型来提高模型的性能和泛化能力。

具体地,您可以将任务定义为预测每个输出,同时利用所有现有工况的数据进行训练。通过干预和随机选择输入变量,您可以创建新工况数据,然后用这些数据来进行测试,以评估您的模型在新工况下的预测性能。在训练期间,您可以使用技巧如随机遗忘来控制模型的权重。

下面是一个示例多任务学习模型的Keras代码:

from keras.models import Model
from keras.layers import Input, Dense, Concatenate

# 输入、输出维度和任务数量
input_dim = 10
output_dim = 5
num_tasks = 5

# 定义输入层
inputs = Input(shape=(input_dim,))

# 定义底层模型(多层感知器)
hidden1 = Dense(64, activation='relu')(inputs)
hidden2 = Dense(64, activation='relu')(hidden1)
hidden3 = Dense(32, activation='relu')(hidden2)

# 定义输出层
task_outputs = []
for i in range(num_tasks):
    task_output = Dense(output_dim, activation='linear')(hidden3)
    task_outputs.append(task_output)

# 合并不同任务的输出
outputs = Concatenate(axis=1)(task_outputs)

# 定义多任务学习模型
model = Model(inputs=inputs, outputs=outputs)

# 编译模型
model.compile(optimizer='rmsprop', loss='mse')

在这个示例中,底层模型采用多层感知器。每个任务都有一个对应的输出层,这些输出层使用共享的底层模型。最后,将不同任务的输出轴合并。模型通过均方误差(MSE)作为损失函数来训练。

  • 这有个类似的问题, 你可以参考下: https://ask.csdn.net/questions/7629579
  • 这篇博客你也可以参考下:从键盘输入一系列字符(以回车键结束),并按字母、数字及其它字符分类统计,最后显示这三类的统计结果
  • 除此之外, 这篇博客: 2020华数杯C题脱贫帮扶绩效评价你怕了吗?中的 问题二:160 个帮扶单位帮扶着基础不同的村庄,帮扶单位帮扶工作的态度、目标、投入、帮扶干部素质等显然是有差异的。仅仅用 2020 年各村庄评分高低显然是无法真正有效的体现一个帮扶单位在脱贫攻坚提升方面所做出的努力。请你运用附件的数据,阐明什么类型的帮扶单位,哪些帮扶单位在脱贫帮扶上面有较高的绩效?请给不同类型的帮扶单位绩效排序,给出脱贫帮扶绩效前十名的帮扶单位编号。 部分也许能够解决你的问题, 你可以仔细阅读以下内容或跳转源博客中阅读:
  • 基本思路是:构造指标-计算各指标的权重-TOPSIS法进行评价
    为了有效凸显出五年来帮扶单位在脱贫攻坚提升方面所作出的努力,计算了各指标的增长率,即

    2020_SR/2015_SR,2020_CY/2015_CY,……,2020_ZF/2015_ZF
    主成分分析法是一种线性无监督的降维方法,可以通过主成分分析法计算各指标方差贡献率,以此作为各指标的权重。接着采用TOPSIS法进行评价,TOPSIS法是一种常用的组内综合评价方法,能充分利用原始数据的信息,其结果能精确地反映各评价方案之间的差距。基本过程为基于归一化后的原始数据矩阵,采用余弦法找出有限方案中的最优方案和最劣方案,然后分别计算各评价对象与最优方案和最劣方案间的距离,获得各评价对象与最优方案的相对接近程度,以此作为评价优劣的依据。该方法对数据分布及样本含量没有严格限制,数据计算简单易行。

    #构造评价指标
    data_2 = pd.DataFrame(data.pivot_table(index=['帮扶单位(0-159)','村庄编号','帮扶单位类型(0-5)'],values=columns)).reset_index()
    for j in range(6):
        data_2['{}_增长率'.format(j)] =  data_2.iloc[:,9+j]/data_2.iloc[:,j+3]
        
    data_2 = data_2.drop(['帮扶单位(0-159)','村庄编号','帮扶单位类型(0-5)'],axis=1).drop(columns,axis=1)
    c = ['CY_增长率','HJ_增长率','SR_增长率','SS_增长率','WJ_增长率','ZF_增长率']
    data_2.columns = c
    
    # 数据归一化
    def Standard(data):
        return (data - data.min())/(data.max()-data.min())
    data_2 = Standard(data_2)
    
    # PCA计算指标权重
    from sklearn.decomposition import PCA
    from sklearn import preprocessing
    pca = PCA(n_components=6)
    pca.fit_transform(data_2)
    weight = pca.explained_variance_ratio_  #方差贡献率
    print(weight)
    
    def topsis(data, weight):
        # 最优最劣方案
        Z = pd.DataFrame([data.min(), data.max()], index=['负理想解', '正理想解'])
        # 距离
        Result = data.copy()
        Result['正理想解'] = np.sqrt(((data - Z.loc['正理想解']) ** 2 * weight).sum(axis=1))
        Result['负理想解'] = np.sqrt(((data - Z.loc['负理想解']) ** 2 * weight).sum(axis=1))
        # 综合得分指数
        Result['综合得分指数'] = Result['负理想解'] / (Result['负理想解'] + Result['正理想解'])
        Result['排序'] = Result.rank(ascending=False)['综合得分指数']
        return Result
    results = topsis(data_2,weight)
    
    results['帮扶单位(0-159)'] = data['帮扶单位(0-159)']
    results['帮扶单位类型(0-5)'] = data['帮扶单位类型(0-5)']
    results.sort_values(by='排序').head(10)
  • 您还可以看一下 李月喜老师的企业微信开发自建内部应用开发篇课程中的 开发文档如何阅读,如何寻求帮助,如何找到同行小节, 巩固相关知识点

以下答案由GPT-3.5大模型与博主波罗歌共同编写:
解决这个问题需要建立一个神经网络多时序并列的模型。常见的方法有LSTM、GRU、Transformer等,这里我们以LSTM为例来说明如何建立模型。

首先,将10个输入作为模型的输入层,5个输出作为模型的输出层,中间加入若干个LSTM层,构建神经网络模型。

然后,为了使模型可以对所有组合出的工况进行预测,需要采用一些技巧。

第一步,将每个工况的输入数据进行one-hot编码,使得每个工况都有唯一的输入数据。

第二步,将所有不同工况的训练数据都输入到模型中进行训练,但是对于每个工况只取其对应的输出数据进行损失的计算。这样可以使得模型学习到所有不同工况的输出规律。

第三步,对于新的工况,将其输入进行one-hot编码后,输入到已经训练好的模型中进行预测,得到其对应的输出结果。

以下是一个简单的代码示例:

import numpy as np
from keras.models import Sequential
from keras.layers import LSTM, Dense, Dropout

# 生成一些随机数据作为模拟数据
np.random.seed(1)
data = np.random.rand(1000, 10)
labels = np.random.rand(1000, 5)

# 建立神经网络模型
model = Sequential()
model.add(LSTM(128, input_shape=(1, 10)))
model.add(Dense(64))
model.add(Dropout(0.2))
model.add(Dense(5, activation='sigmoid'))

# 编译模型
model.compile(loss='mse', optimizer='adam')

# 将所有不同工况的数据都输入到模型中进行训练
for i in range(n):
    x_train = data[i*100:(i+1)*100]
    y_train = labels[i*100:(i+1)*100]
    model.fit(np.expand_dims(x_train, axis=1), y_train, epochs=10, batch_size=32)

# 预测新的工况的输出结果
new_x = np.random.rand(1, 10)
new_x_encoded = ... # 对新的工况输入进行one-hot编码
new_y = model.predict(np.expand_dims(new_x_encoded, axis=1))

注意,以上代码是一个简单的示例,具体的实现需要根据实际情况进行调整和优化。
如果我的回答解决了您的问题,请采纳!

以下答案由GPT-4.5Plus大模型(语音)与博主A努力中.......共同编写:

这是一个多输入多输出的时间序列预测问题。要建立一个可以预测所有工况的模型,可以考虑以下步骤:

  1. 收集尽可能多的工况数据。要实现泛化预测,模型需要在训练过程中“学习”到不同工况之间的内在关系与规律,所以数据越多越好。
  2. 考虑使用LSTM等RNN模型。RNN模型专为序列建模设计,可以捕捉时间维度的动态特征,适合此类问题。
  3. 使用一个模型同时预测所有输出。不要为不同输出建立独立模型,应构建一个统一模型,所有输出共用同一个LSTM层等。这可以让模型自动学习不同输出之间的相关性,从而实现泛化。
  4. 利用丢弃法或正则化防止过拟合。由于只有部分工况的数据,容易过拟合,应在模型中添加丢弃层、L1/L2正则化等来提高泛化能力。
  5. 调参时同时考虑所有输出的性能。不要为每个输出单独调参,要综合考虑多个输出的预测效果来选择最优模型和参数。这也是让模型学会关注不同输出之间的相关性的一种方式。
  6. 生成测试集包含尽可能全的工况组合。只用seen数据评估不足以判断泛化能力,要生成不同工况组合的测试数据来评估模型对新工况的预测能力。

一个简单的模型结构可以是:

input1 = Input(shape=( lookback, input_dim1)) 
input2 = Input(shape=( lookback, input_dim2)) 
...
input10 = Input(shape=( lookback, input_dim10))

lstm_out = LSTM(32)(input1, input2, ..., input10)

output1 = Dense(1)(lstm_out) 
output2 = Dense(1)(lstm_out)
...
output5 = Dense(1)(lstm_out)

model = Model([input1, input2, ..., input10], [output1, output2, ..., output5])

希望这个方案和解释能对你在此问题上提供帮助。