linear-regression - PyTorch 不会将直线拟合到两个数据点
问题描述
我在使用 pytorch 拟合带有 2 个数据点的简单 y=4x1 线时遇到问题。在运行推理代码时,模型似乎向任何奇怪的输入输出相同的值。请找到随附的代码以及我使用的数据文件。感谢这里的任何帮助。
import torch
import numpy as np
import pandas as pd
df = pd.read_csv('data.csv')
test_data = pd.read_csv('test_data.csv')
inputs = df[['x1']]
target = df['y']
inputs = torch.tensor(inputs.values).float()
target = torch.tensor(target.values).float()
test_data = torch.tensor(test_data.values).float()
#Defining Network Architecture
import torch.nn as nn
import torch.nn.functional as F
class Net(nn.Module):
def __init__(self):
super(Net,self).__init__()
hidden1 = 3
# hidden2 = 5
self.fc1 = nn.Linear(1,hidden1)
self.fc3 = nn.Linear(hidden1,1)
def forward(self,x):
x = F.relu(self.fc1(x))
x = self.fc3(x)
return x
#instantiate the model
model = Net()
print(model)
criterion = nn.MSELoss()
optimizer = torch.optim.SGD(model.parameters(),lr=0.01)
model.train()
#epochs
epochs = 100
for x in range(epochs):
#initialize the training loss to 0
train_loss = 0
#clear out gradients
optimizer.zero_grad()
#calculate the output
output = model(inputs)
#calculate loss
loss = criterion(output,target)
#backpropagate
loss.backward()
#update parameters
optimizer.step()
if ((x%5)==0):
print('Training Loss after epoch {:2d} is {:2.6f}'.format(x,loss))
#set the model in evaluation mode
model.eval()
#Test the model on unseen data
test_output = model(test_data)
print(test_output)
下面是模型输出
#model output
tensor([[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579],
[56.7579]], grad_fn=<AddmmBackward>)
解决方案
你的模型正在崩溃。您可能会看到基于prints
. 您可能希望使用较低的学习率(1e-5、1e-6 等)。如果您没有经验并且希望减少微调这些 hparams 的麻烦,从 切换SGD(...)
到可能会更容易。Adam(...)
此外,也许 100 个 epoch 是不够的。由于您没有共享MCVE,我无法确定它是什么。这是使用与您使用的相同的线拟合的MCVE :Net
import torch
import numpy as np
import torch.nn as nn
import torch.nn.functional as F
epochs = 1000
max_range = 40
interval = 4
# DATA
x_train = torch.arange(0, max_range, interval).view(-1, 1).float()
x_train += torch.rand(x_train.size(0), 1) - 0.5 # small noise
y_train = (4 * x_train)
y_train += torch.rand(x_train.size(0), 1) - 0.5 # small noise
x_test = torch.arange(interval // 2, max_range, interval).view(-1, 1).float()
y_test = 4 * x_test
class Net(nn.Module):
def __init__(self):
super(Net, self).__init__()
hidden1 = 3
self.fc1 = nn.Linear(1, hidden1)
self.fc3 = nn.Linear(hidden1, 1)
def forward(self, x):
x = F.relu(self.fc1(x))
x = self.fc3(x)
return x
model = Net()
print(model)
criterion = nn.MSELoss()
optimizer = torch.optim.SGD(model.parameters(), lr=1e-5)
# TRAIN
model.train()
for epoch in range(epochs):
optimizer.zero_grad()
y_pred = model(x_train)
loss = criterion(y_pred, y_train)
loss.backward()
optimizer.step()
if epoch % 10 == 0:
print('Training Loss after epoch {:2d} is {:2.6f}'.format(epoch, loss))
# TEST
model.eval()
y_pred = model(x_test)
print(torch.cat((x_test, y_pred, y_test), dim=-1))
这是数据的样子:
这就是培训的样子:
Training Loss after epoch 0 is 7416.805664
Training Loss after epoch 10 is 6645.655273
Training Loss after epoch 20 is 5792.936523
Training Loss after epoch 30 is 4700.106445
Training Loss after epoch 40 is 3245.384277
Training Loss after epoch 50 is 1779.370728
Training Loss after epoch 60 is 747.418579
Training Loss after epoch 70 is 246.781311
Training Loss after epoch 80 is 68.635155
Training Loss after epoch 90 is 17.332235
Training Loss after epoch 100 is 4.280161
Training Loss after epoch 110 is 1.170808
Training Loss after epoch 120 is 0.453974
...
Training Loss after epoch 970 is 0.232296
Training Loss after epoch 980 is 0.232090
Training Loss after epoch 990 is 0.231888
这就是输出的样子:
| x_test | y_pred | y_test |
|:-------:|:--------:|:--------:|
| 2.0000 | 8.6135 | 8.0000 |
| 6.0000 | 24.5276 | 24.0000 |
| 10.0000 | 40.4418 | 40.0000 |
| 14.0000 | 56.3303 | 56.0000 |
| 18.0000 | 72.1884 | 72.0000 |
| 22.0000 | 88.0465 | 88.0000 |
| 26.0000 | 103.9047 | 104.0000 |
| 30.0000 | 119.7628 | 120.0000 |
| 34.0000 | 135.6210 | 136.0000 |
| 38.0000 | 151.4791 | 152.0000 |
推荐阅读
- javascript - 如何在 Javascript 中像社交媒体提要一样输出数组?
- javascript - 网格 EXTJ 中的循环
- node.js - Node.js 没有创建目录
- php - Laravel 控制器充当代理
- compilation - Samba 4.9.1 密码与 CentOS7 root 密码同步
- oracle - 第一行 VS 下一行 VS rownum
- javascript - 如果相机在 instascan 中打开,输入类型不起作用
- javascript - 使用 Lodash 根据另一个对象的真实状态获取对象的值
- azure - CORS 异常:无法加载 https://login.microsoftonline.com/{TENANT_ID}/oauth2/authorize
- sql - 将数据类型 varchar 转换为日期时将 int 年份转换为字符串时出错