1 | import torch |
'1.3.1'
0x00 基础
tensor基础
1 | x = torch.rand(5, 3) |
<class 'builtin_function_or_method'>
torch.Size([5, 3])
tensor([[1., 1., 1.],
[1., 1., 1.],
[1., 1., 1.],
[1., 1., 1.],
[1., 1., 1.]], dtype=torch.float64)
tensor([[1.4885, 1.3968, 1.5492],
[1.2027, 1.9136, 1.1277],
[1.2467, 1.5696, 1.7672],
[1.6679, 1.0424, 1.4230],
[1.0175, 1.9733, 1.7792]], dtype=torch.float64)
1 | # 方法二 |
1 | print(y[:,1]) |
tensor([0.3968, 0.9136, 0.5696, 0.0424, 0.9733])
1 | x = torch.randn(4, 4) |
torch.Size([4, 4]) torch.Size([16])
1 | x = torch.randn(4, 4) |
torch.Size([4, 4])
1 | y = x.view(2, 8) |
torch.Size([4, 4]) torch.Size([2, 8])
0.7401983737945557
Numpy 相关操作
tensor2numpy
将张量转换成numpy数组
1 | a = torch.ones(5) |
tensor([1., 1., 1., 1., 1.])
[1. 1. 1. 1. 1.]
将张量+1,并观察上题中numpy数组的变化
1 | a.add_(1) |
tensor([2., 2., 2., 2., 2.])
[2. 2. 2. 2. 2.]
从numpy数组创建张量
1 | import numpy as np |
tensor([1., 1., 1., 1.], dtype=torch.float64)
将numpy数组+1并观察上题中张量的变化
1 | np.add(a, 1, out=a) |
[2. 2. 2. 2.]
tensor([2., 2., 2., 2.], dtype=torch.float64)
自动微分
张量的自动微分
新建一个张量,并设置requires_grad=True
1 | x = torch.ones(2, 2, requires_grad=True) |
tensor([[1., 1.],
[1., 1.]], requires_grad=True)
对张量进行任意操作(y = x + 2)
1 | y = 2*x**2 + 1 |
tensor([[3., 3.],
[3., 3.]], grad_fn=<AddBackward0>)
<AddBackward0 object at 0x000001FE254F3828>
1 | z = y ** 2 * 3 |
tensor([[27., 27.],
[27., 27.]], grad_fn=<MulBackward0>)
tensor(27., grad_fn=<MeanBackward0>)
梯度
1 | out.backward() |
1 | print(x.grad) |
tensor([[18., 18.],
[18., 18.]])
创建一个结果为矢量的计算过程(y=x*2^n)
1 | x = torch.randn(3, requires_grad=True) |
tensor([-59.5318, 726.0163, 771.8844], grad_fn=<MulBackward0>)
计算v = [0.1, 1.0, 0.0001]处的梯度
1 | v = torch.tensor([0.1, 1.0, 0.0001], dtype=torch.float) |
tensor([5.1200e+01, 5.1200e+02, 5.1200e-02])
关闭梯度的功能
1 | print(x.requires_grad) |
True
True
False
True
False
tensor(True)
pytorch a.equal(b) 与a.eq(b)
a,b是两个列表;
a.equal(b)要求整个列表完全相同才是True;
a.eq(b) 相同位置值相同则返回对应的True,返回的是一个列表.
神经网络
定义网络
1 | import torch |
Net(
(conv1): Conv2d(3, 6, kernel_size=(5, 5), stride=(1, 1))
(conv2): Conv2d(6, 16, kernel_size=(5, 5), stride=(1, 1))
(fc1): Linear(in_features=400, out_features=120, bias=True)
(fc2): Linear(in_features=120, out_features=84, bias=True)
(fc3): Linear(in_features=84, out_features=10, bias=True)
)
1 | # 打印网络的参数 |
10
torch.Size([6, 3, 5, 5])
1 | #随机输入一个向量,查看前向传播输出 |
tensor([[-0.0495, 0.0040, -0.0026, -0.0695, -0.0843, 0.0612, 0.1408, -0.0546,
-0.0449, -0.0566]], grad_fn=<AddmmBackward>)
1 | #将梯度初始化 |
1 | print(net.conv1.bias.grad) |
tensor([ 0.0215, 0.0639, -0.0101, 0.0102, 0.0425, 0.0004])
损失函数
用自带的MSELoss()定义损失函数
1 | criterion = nn.MSELoss() |
tensor(0.8646, grad_fn=<MseLossBackward>)
1 | # 将梯度初始化,计算上一步中loss的反向传播 |
conv1.bias.grad before backward
tensor([0., 0., 0., 0., 0., 0.])
1 | # 计算上上一步中loss的反向传播 |
conv1.bias.grad after backward
tensor([0.0072, 0.0010, 0.0057, 0.0040, 0.0094, 0.0036])
更新权重
定义SGD优化器算法,学习率设置为0.01
1 | import torch.optim as optim |
训练一个分类器
读取CIFAR10数据,做标准化
构造一个transform,将三通道(0,1)区间的数据转换成(-1,1)的数据
1 | import torchvision |
1 | # 读取数据集 |
1 | net2 = Net() |
1 | for epoch in range(2): |
Finished Training
1 | import matplotlib.pyplot as plt |
GroundTruth: cat ship ship plane
torch.Size([3, 240, 274])
1 | outputs = net2(images) |
Predicted: cat ship ship ship
1 | correct = 0 |
Accuracy of the network on the 10000 test images: 39 %
1 | # 4.6 存取模型 |
Tips
- Parameter类其实是Tensor的子类
- PyTorch的 transpose、permute、view、reshape
- https://www.jianshu.com/p/54f5ccba4057
- reshape 封装了 view,view根据规则有时还需要调用contiguous()
- permute().contiguous().view()相当于reshape
- permute() 和 tranpose() 比较相似,transpose是交换两个维度,permute()是交换多个维度。
产生分布的函数
函数 | 功能 |
---|---|
tensor.uniform_(-10, 10) | 均匀分布 |
tensor.normal_(mean, std) | 标准正态分布 |
一些基本操作
函数 | 功能 |
---|---|
trace | 对角线元素之和(矩阵的迹) |
diag | 对角线元素 |
triu/tril | 矩阵的上三角/下三角,可指定偏移量 |
mm/bmm | 矩阵乘法,batch的矩阵乘法 |
addmm/addbmm/addmv/addr/baddbmm.. | 矩阵运算 |
t | 转置 |
dot/cross | 内积/外积 |
inverse | 求逆矩阵 |
svd | 奇异值分解 |
PyTorch中的Tensor支持超过一百种操作,包括转置、索引、切片、数学运算、线性代数、随机数等等,可参考官方文档。
Ques
- log_softmax比softmax多计算一次log,意义在于 加快计算速度,数值上也更稳定。 参考资料:PyTorch学习笔记——softmax和log_softmax的区别、CrossEntropyLoss() 与 NLLLoss() 的区别、log似然代价函数
- Pytorch中torch.nn.Softmax的dim参数含义 就是在第几维上 sum=1
tf.nn.softmax中dim默认为-1,即,tf.nn.softmax会以最后一个维度作为一维向量计算softmax 注意:tf.nn.softmax函数默认(dim=-1)是对张量最后一维的shape=(p,)向量进行softmax计算,得到一个概率向量。不同的是,tf.nn.sigmoid函数对一个张量的每一个标量元素求得一个概率。也就是说tf.nn.softmax默认针对1阶张量进行运算,可以通过指定dim来针对1阶以上的张量进行运算,但不能对0阶张量进行运算。而tf.nn.sigmoid是针对0阶张量,。 参考资料:tensorflow中交叉熵系列函数
???? python 深拷贝、浅拷贝
- mean std(标准差)
- ???? numpy.triu torch.from_numpy
- ???? 负的维度的使用
- ???? torch.view .transpose
- ???? 标签平滑 KL散度评价