一些简单操作
import torch
x = torch.empty(5, 3) # 构建空矩阵
y = torch.zeros(5, 3, dtype = torch.long) # 构建0矩阵
z = torch.ones(5, 3, dtpye = torch.double) # 全 1
z0 = torch.randn_like(x, dtype = torch.float) # 和z有同样shape
m = torch.rand(5, 3) # 0~1 均匀分布
x.size() # 可以看tensor的shape
x.view(-1, 4) # view函数改变shape
- 这几个操作对应的格式都是tensor, 也类似numpy的操作
与numpy的协同操作
1. 转化为numpy相关格式
a = torch.ones(5)
b = a.numpy()
print(type(b))
>>
<class 'numpy.ndarray'>
2. 从numpy转换
import numpy
import torch
c = numpy.ones(5)
d = torch.from_numpy(c)
print(d)
>>
tensor([1., 1., 1., 1., 1.], dtype=torch.float64)
自动求导机制
a = torch.ones(3, 4, requires_grad=True)
b = torch.ones(3, 4, requires_grad=True)
c = a + b
y = c.sum()
y.backward()
print(b.grad)
>>
tensor([[1., 1., 1., 1.],
[1., 1., 1., 1.],
[1., 1., 1., 1.]])
举个简单的例子
x = torch.rand(1)
b = torch.rand(1, requires_grad=True)
w = torch.rand(1, requires_grad=True)
y = w * x
z = y + b
z.backward()
print(b.grad)
>>
tensor([1.])
- 注意只有叶节点的grad才可以输出
Pytorch中retain_graph参数的作用
import torch
x = torch.randn((1,4),dtype=torch.float32,requires_grad=True)
y = x ** 2
z = y * 4
output1 = z.mean()
output2 = z.sum()
output1.backward()
# 这个代码执行正常,但是执行完中间变量都free了,所以下一个出现了问题
output2.backward() # 这时会引发错误
简单的线性模型例子
import torch
import numpy as np
x_value = [i for i in range(11)]
y_value = [2*i+1 for i in x_value]
x_train = np.array(x_value, dtype=np.float32).reshape(-1, 1)
# 首先转化为numpy格式再转化为tensor格式
x_train = torch.from_numpy(x_train)
y_train = np.array(y_value, dtype=np.float32).reshape(-1, 1)
y_train = torch.from_numpy(y_train)
class LinearModel(torch.nn.Module):
def __init__(self, input_dim, output_dim):
super().__init__()
self.linear = torch.nn.Linear(input_dim, output_dim)
def forward(self, x):
return self.linear(x)
# 定义参数
input_dim = 1
output_dim = 1
epoches = 1000
learning_rate = 0.01
# 设置model
model = LinearModel(input_dim, output_dim)
optimizer = torch.optim.SGD(model.parameters(), lr=learning_rate)
criterion = torch.nn.MSELoss()
for epoch in range(epoches):
epoch += 1
y_pre = model(x_train)
loss = criterion(y_pre, y_train)
optimizer.zero_grad()
loss.backward()
optimizer.step() # 更新参数
if epoch % 50 ==0:
print('epoch:{}, loss:{}'.format(epoch, loss))
# 验证效果
with torch.no_grad():
y = model(x_train)
print(y.requires_grad) # 验证是否存在梯度的计算
z = y.data.numpy() # 因为一开始没有梯度,所以y.numpy()也是可以的
print(z)
保存模型
torch.save(model.state_dict, 'model.pkl')
model.load_state_dict(torch.load('model.pkl'))
使用GPU进行训练
- 需要把数据和模型传入GPU, 所以有三个点
1. device 2. 模型的传入 3. 数据的传入
device = torch.device('cuda:0' if torch.cuda.is_available() else 'cpu')
model.to(device)
x_train = x_train.to(device)
y_train = y_train.to(device)
# 这个y_pre就不用放进去了, 因为x_train已经好了