用pytorch写一个天气预测的代码,用LSTM或CNN,读取天气中的csv文件,由时间和气温两列数据,区分训练集和测试集,用gpu训练,输入为60天的天气,输出为某一天的天气,并画出60天的实际曲线和预测曲线图,注意维度要一致
时间: 2023-09-30 09:06:03 浏览: 37
好的,以下是一个使用LSTM模型进行天气预测的代码:
```python
import torch
import torch.nn as nn
import torch.optim as optim
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
# 读取数据
data = pd.read_csv('weather.csv')
time = data['Time'].values.astype(str)
temp = data['Temperature'].values.astype(float)
# 数据归一化
temp_max = np.max(temp)
temp_min = np.min(temp)
temp = (temp - temp_min) / (temp_max - temp_min)
# 构建训练集和测试集
train_size = int(len(temp) * 0.8)
train_temp = temp[:train_size]
test_temp = temp[train_size:]
# 定义超参数
input_size = 60
output_size = 1
hidden_size = 64
num_layers = 2
learning_rate = 0.01
num_epochs = 100
# 定义模型
class WeatherPredictor(nn.Module):
def __init__(self, input_size, hidden_size, output_size, num_layers):
super(WeatherPredictor, self).__init__()
self.hidden_size = hidden_size
self.num_layers = num_layers
self.lstm = nn.LSTM(input_size, hidden_size, num_layers, batch_first=True)
self.fc = nn.Linear(hidden_size, output_size)
def forward(self, x):
h0 = torch.zeros(self.num_layers, x.size(0), self.hidden_size).to(device)
c0 = torch.zeros(self.num_layers, x.size(0), self.hidden_size).to(device)
out, _ = self.lstm(x, (h0, c0))
out = self.fc(out[:, -1, :])
return out
# 初始化模型和损失函数
device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')
model = WeatherPredictor(input_size, hidden_size, output_size, num_layers).to(device)
criterion = nn.MSELoss()
optimizer = optim.Adam(model.parameters(), lr=learning_rate)
# 训练模型
train_losses = []
test_losses = []
for epoch in range(num_epochs):
model.train()
inputs = []
targets = []
for i in range(input_size, len(train_temp)):
inputs.append(train_temp[i-input_size:i])
targets.append(train_temp[i])
inputs = np.array(inputs)
targets = np.array(targets)
inputs = torch.from_numpy(inputs).float().to(device)
targets = torch.from_numpy(targets).float().to(device)
optimizer.zero_grad()
outputs = model(inputs)
loss = criterion(outputs, targets)
loss.backward()
optimizer.step()
train_losses.append(loss.item())
# 在测试集上计算损失
model.eval()
inputs = []
targets = []
for i in range(input_size, len(test_temp)):
inputs.append(test_temp[i-input_size:i])
targets.append(test_temp[i])
inputs = np.array(inputs)
targets = np.array(targets)
inputs = torch.from_numpy(inputs).float().to(device)
targets = torch.from_numpy(targets).float().to(device)
with torch.no_grad():
outputs = model(inputs)
loss = criterion(outputs, targets)
test_losses.append(loss.item())
if (epoch+1) % 10 == 0:
print(f'Epoch [{epoch+1}/{num_epochs}], Train Loss: {loss.item():.4f}, Test Loss: {loss.item():.4f}')
# 进行预测
model.eval()
inputs = test_temp[-input_size:]
predictions = []
for i in range(output_size):
input_data = inputs[-input_size:]
input_data = np.array(input_data).reshape(1, input_size, 1)
input_data = torch.from_numpy(input_data).float().to(device)
with torch.no_grad():
output = model(input_data)
output = output.cpu().numpy()
predictions.append(output[0][0])
inputs = np.concatenate((inputs, output), axis=0)
# 反归一化
train_temp = train_temp * (temp_max - temp_min) + temp_min
test_temp = test_temp * (temp_max - temp_min) + temp_min
predictions = np.array(predictions) * (temp_max - temp_min) + temp_min
# 绘制实际曲线和预测曲线图
plt.plot(time[train_size+input_size:], test_temp, label='Actual')
plt.plot(time[train_size+input_size:], predictions, label='Predicted')
plt.xlabel('Time')
plt.ylabel('Temperature')
plt.legend()
plt.show()
```
其中,`weather.csv`是包含时间和气温两列数据的CSV文件。代码中使用了LSTM模型进行天气预测,将数据归一化后,使用前80%的数据作为训练集,后20%的数据作为测试集。模型训练完成后,使用测试集进行预测,并将预测结果反归一化后,绘制出实际曲线和预测曲线图。