入门
1. 张量
Tensor与Numpy的ndarray类似,而且,Tensor还可以在GPU上进行更快的计算
- 构造一个未初始化的矩阵(5x3)
import torch
x = torch.empty(5, 3)
print(x)
tensor([[1.8040e+28, 1.8750e-19, 7.3909e+22],
[2.4176e-12, 2.6209e+20, 4.1641e+12],
[8.9625e-01, 7.9309e+34, 7.9439e+08],
[3.2604e-12, 7.3113e+34, 9.5492e-01],
[7.3154e+34, 5.9682e-02, 7.0374e+22]])
- 构造一个随机初始化的矩阵
x = torch.rand(5, 3)
print(x)
tensor([[0.9989, 0.0300, 0.9897],
[0.5019, 0.7720, 0.4907],
[0.1719, 0.9210, 0.5989],
[0.3449, 0.5236, 0.2488],
[0.7316, 0.2383, 0.4826]])
- 构造一个用0填充且的type为long的矩阵
x = torch.zeros(5, 3, dtype=torch.long)
x
tensor([[0, 0, 0],
[0, 0, 0],
[0, 0, 0],
[0, 0, 0],
[0, 0, 0]])
- 从数据直接构造张量
x = torch.tensor([5.5, 3])
x
tensor([5.5000, 3.0000])
- 基于现有的张量创建张量,这些方法将重用输入张量的属性,例如dtype,除非提供新的值
x = x.new_ones(5, 3, dtype=torch.double)
x
tensor([[1., 1., 1.],
[1., 1., 1.],
[1., 1., 1.],
[1., 1., 1.],
[1., 1., 1.]], dtype=torch.float64)
x = torch.randn_like(x, dtype=torch.float)
x
tensor([[-0.7570, 0.3496, 0.2732],
[-1.1484, -0.0426, -0.4377],
[-0.4407, 1.3456, -0.7647],
[ 0.6696, 0.0505, -0.6712],
[ 0.1903, -0.4523, -0.3878]])
- 得到张量的大小
x.size()
torch.Size([5, 3])
PS: torch.Size是一个元组,支持所有的元组操作
2. 运算
2.1 加法
- 语法1:
y = torch.rand(5,3)
x + y
tensor([[-0.6037, 0.8618, 0.5876],
[-0.8242, 0.8127, 0.3994],
[ 0.1560, 2.2990, -0.7292],
[ 0.9237, 0.4621, -0.5015],
[ 0.2923, -0.1390, -0.1539]])
- 语法2:
torch.add(x, y)
tensor([[-0.6037, 0.8618, 0.5876],
[-0.8242, 0.8127, 0.3994],
[ 0.1560, 2.2990, -0.7292],
[ 0.9237, 0.4621, -0.5015],
[ 0.2923, -0.1390, -0.1539]])
- 加法可以提供输出张量作为参数
res = torch.empty(5, 3)
torch.add(x, y, out=res)
res
tensor([[-0.6037, 0.8618, 0.5876],
[-0.8242, 0.8127, 0.3994],
[ 0.1560, 2.2990, -0.7292],
[ 0.9237, 0.4621, -0.5015],
[ 0.2923, -0.1390, -0.1539]])
- 原地加法
y.add_(x)
y
tensor([[-0.6037, 0.8618, 0.5876],
[-0.8242, 0.8127, 0.3994],
[ 0.1560, 2.2990, -0.7292],
[ 0.9237, 0.4621, -0.5015],
[ 0.2923, -0.1390, -0.1539]])
PS: 使用张量原地变化的运算都固定,如:x.copy_(y), x.t_()这会改变x.
- 可以使用类似于NumPy的索引方式
x[:, 1]
tensor([ 0.3496, -0.0426, 1.3456, 0.0505, -0.4523])
2.2 调整大小
- 调整张量的大小和形状,可以用torch.view
x = torch.randn(4, 4)
y = x.view(16)
y
tensor([-0.1874, -1.0778, 1.2749, 0.9475, 1.2493, -0.2680, -0.8600, -1.7123,
0.0466, 0.5409, -0.0982, -0.0890, 0.9033, -0.3264, -0.1038, -0.2352])
z = x.view(-1, 8)# 注意这个-1
z
tensor([[-0.1874, -1.0778, 1.2749, 0.9475, 1.2493, -0.2680, -0.8600, -1.7123],
[ 0.0466, 0.5409, -0.0982, -0.0890, 0.9033, -0.3264, -0.1038, -0.2352]])
3 NumPy与Tensor的转换
可以很容易地将NumPy的数组与Torch的张量相互转化
Torch地Tensor和NumPy数组将共享内存位置(前提是Torch在CPU的内存中),并且更改其中一个将会更改另一个
- 将Torch 张量转化为NumPy数组
a = torch.ones(5)
a
tensor([1., 1., 1., 1., 1.])
b = a.numpy()
b
array([1., 1., 1., 1., 1.], dtype=float32)
- 查看NumPy数组的值如何变化
a.add_(1)
print(a)
print(b)
tensor([2., 2., 2., 2., 2.])
[2. 2. 2. 2. 2.]
- 将NumPy数组转化为Torch的张量
import numpy as np
a = np.ones(5)
b = torch.from_numpy(a)
np.add(a, 1, out=a)
print(a)
print(b)
[2. 2. 2. 2. 2.]
tensor([2., 2., 2., 2., 2.], dtype=torch.float64)
PS: 除了CharTensor之外,CPU上的所有张量都支持转化为NumPy并返回
- 使用.to方法可以将张量移动到任何设备上.
if torch.cuda.is_available():
device = torch.device("cuda")
y = torch.ones_like(x, device=device)
x = x.to(device)
z = x + y
print(z)
print(z.to("cpu", torch.double))
tensor([[ 0.8126, -0.0778, 2.2749, 1.9475],
[ 2.2493, 0.7320, 0.1400, -0.7123],
[ 1.0466, 1.5409, 0.9018, 0.9110],
[ 1.9033, 0.6736, 0.8962, 0.7648]], device='cuda:0')
tensor([[ 0.8126, -0.0778, 2.2749, 1.9475],
[ 2.2493, 0.7320, 0.1400, -0.7123],
[ 1.0466, 1.5409, 0.9018, 0.9110],
[ 1.9033, 0.6736, 0.8962, 0.7648]], dtype=torch.float64)