目录
1. 初始化Tnesor
1.1 直接从数据
1.2 来自Numpy数组
1.3 来自另一个Tensor
1.4 使用随机值或固定值
2. Tensor的属性
3. Tensor的运算
3.1 类似 numpy 的索引和切片
3.2 链接Tensor
3.3 算术运算
3.4 转化为Python 数值
3.5 就地操作
4. 与Numpy桥接
4.1 Tensor到Numpy数组
4.2 Numpy数组到Tensor
data = [[1, 2],[3, 4]]
x_data = torch.tensor(data)
np_array = np.array(data)
x_np = torch.from_numpy(np_array)
# retains the properties of x_data
x_ones = torch.ones_like(x_data)
# overrides the datatype of x_data
x_rand = torch.rand_like(x_data, dtype=torch.float)
shape = (2,3,)
rand_tensor = torch.rand(shape)
ones_tensor = torch.ones(shape)
zeros_tensor = torch.zeros(shape)
Tensor属性描述了它们的形状、数据类型和存储它们的设备。
tensor = torch.rand(3,4)
print(tensor.shape)
print(tensor.dtype)
print(tensor.device)
out:
>> torch.Size([3, 4])
>> torch.float32
>> cpu
更全面的Tensor运算介绍可点击这里。
所有Tensor运算均可以在GPU上运行,并且通常有比CPU更高的速度。默认情况下,Tensor是在 CPU 上创建的。我们需要使用 .to 方法(在检查 GPU 可用性之后)将Tensor显式移动到 GPU上。
if torch.cuda.is_available():
tensor = tensor.to("cuda")
tensor = torch.ones(4, 4)
print(f"First row: {tensor[0]}")
print(f"First column: {tensor[:, 0]}")
print(f"Last column: {tensor[..., -1]}")
tensor[:,1] = 0
print(tensor)
out:
>> First row: tensor([1., 1., 1., 1.])
>> First column: tensor([1., 1., 1., 1.])
>> Last column: tensor([1., 1., 1., 1.])
>> tensor([[1., 0., 1., 1.],
[1., 0., 1., 1.],
[1., 0., 1., 1.],
[1., 0., 1., 1.]])
可以使用 torch.cat 沿给定维度连接一系列Tensor。此外,还有一个与 torch.cat 略有不同的,可以在新的维度链接Tensor的操作可参阅这里。
t1 = torch.cat([tensor, tensor, tensor], dim=1)
print(t1)
out:
>> tensor([[1., 0., 1., 1., 1., 0., 1., 1., 1., 0., 1., 1.],
[1., 0., 1., 1., 1., 0., 1., 1., 1., 0., 1., 1.],
[1., 0., 1., 1., 1., 0., 1., 1., 1., 0., 1., 1.],
[1., 0., 1., 1., 1., 0., 1., 1., 1., 0., 1., 1.]])
# 计算两个矩阵相乘。 y1, y2, y3具有相同的值。
y1 = tensor @ tensor.T # tensor.T是计算Tensor的转置
y2 = tensor.matmul(tensor.T)
y3 = torch.rand_like(tensor) # tensor.shape是两矩阵相乘后的shape
torch.matmul(tensor, tensor2.T, out=y)
# 这计算的是矩阵元素逐一相乘。 z1, z2, z3具有相同的值。
z1 = tensor * tensor
z2 = tensor.mul(tensor)
z3 = torch.rand_like(tensor)
torch.mul(tensor, tensor, out=z3)
通过 item() 可以讲单元素Tensor转化为Python数值。
agg = tensor.sum() # 通过将tensor的所有值聚合成一个值
agg_item = agg.item()
print(agg_item, type(agg_item))
out:
>> 12.0
将操作结果储存到操作数的操作成为就地操作。常用_后缀表示,例如:x.copy_(y),x.t_(),会直接改变x。
print(tensor, "\n")
tensor.add_(5)
print(tensor)
out:
>>tensor([[1., 0., 1., 1.],
[1., 0., 1., 1.],
[1., 0., 1., 1.],
[1., 0., 1., 1.]])
>>tensor([[6., 5., 6., 6.],
[6., 5., 6., 6.],
[6., 5., 6., 6.],
[6., 5., 6., 6.]])
Note: 就地操作可以节约一些内存,但是计算导数时可能出现问题,因为会立即丢失历史记录。因此不鼓励使用它们。
CPU上的Tensor和Numpy数组可以共享他们的底层内存位置,并且改变其中一个另一个也会改变。
t = torch.ones(5)
print(f"t: {t}")
n = t.numpy()
print(f"n: {n}")
out:
>> t: tensor([1., 1., 1., 1., 1.])
>> n: [1. 1. 1. 1. 1.]
Tensor的变化会反映在Numpy数组中。
t.add_(1)
print(f"t: {t}")
print(f"n: {n}")
out:
>> t: tensor([2., 2., 2., 2., 2.])
>> n: [2. 2. 2. 2. 2.]
n = np.ones(5)
t = torch.from_numpy(n)
NumPy 数组的变化反映在Tensor中。
np.add(n, 1, out=n)
print(f"t: {t}")
print(f"n: {n}")
out:
>> t: tensor([2., 2., 2., 2., 2.], dtype=torch.float64)
>> n: [2. 2. 2. 2. 2.]