一、tensor的相关概念
1、定义:就是多维矩阵。
2、张量的数据类型:
1、查看数据类型和修改
import torch
a=torch.tensor([1.2,3.4]).dtype
用torch.tensor()函数来创建一个张量,用 .dtype 来显式张量的数据类型。
tensor的数据类型默认是32位
import torch
torch.set_default_tensor_type(torch.DoubleTensor)
修改tensor的默认值。
3、张量的生成
1、使用torch.tensor()函数构造张量
(1)
A=torch.tensor([[1.0,1.0],[2,2]])
通过torch.tensor()将python的列表转化为张量。
(2)
.shape获得tensor的维度,.size()获得tensor的形状大小,.numel()获得元素的个数
import torch
A=torch.tensor([[1.0,1.0],[2,2]])
print(A.shape)
print(A.size())
print(A.numel())
#torch.Size([2, 2])
#torch.Size([2, 2])
#4
(3)
在torch.tensor()中可以通过dtype=来设定张量的数据类型,通过requires_grad来设置是否需要计算梯度。
只有计算梯度的tensor才能在深度网络优化时根据梯度大小进行优化。
A=torch.tensor((1,2,3),dtype=torch.float32,requires_grad=True)
(4)
由于requires_grad=True,所以这里计算了A²的梯度=2*A,而且要注意只有是dtype=浮点数的时候才可以计算梯度。
import torch
A=torch.tensor((1,2,3),dtype=torch.float32,requires_grad=True)
y=A.pow(2).sum()
y.backward()
print(A.grad)
2、使用torch.Tensor()来建立张量
(1)根据指定的形状建立
A=torch.Tensor([1,2,3,4])
(2)根据指定的尺寸建立
A=torch.Tensor(2,3)
(3)
- torch.zeros()
功能:依 size 创建全 0 的张量 - torch.zeros_like()
功能:依据 input 形状创建全 0 张量 - torch.ones()
功能:创建全为 1 的张量 - torch.ones_like()
功能:依 input 形状创建全为 1 的张量 - torch.eye()
功能:创建单位对角矩阵(2 维张量)
3、张量与numpy互换
(1)可以相互转化
import torch
import numpy as np
np_data = np.arange(6).reshape((2, 3))
torch_data = torch.from_numpy(np_data)
tensor2array = torch_data.numpy()
print(
'\nnumpy array:', np_data, # [[0 1 2], [3 4 5]]
'\ntorch tensor:', torch_data, # 0 1 2 \n 3 4 5 [torch.LongTensor of size 2x3]
'\ntensor to array:', tensor2array, # [[0 1 2], [3 4 5]]
)
a) 将numpy数据转化为torch:torch.from_numpy(np_data) 、torch.as_torch(np_data)
b) 将torch的数据转换为numpy:torch_data.numpy()
4、随机数生成张量
(1)
import torch
torch.cuda.manual_seed(123)
A=torch.normal(mean=0.0,std=torch.tensor(1.0))
首先建立一个种子,torch.cuda.manual_seed(数字)这里建立的是GPU的种子,去掉.cuda就是cpu种子。
torch.normal(mean=0.0,std=torch.tensor(1.0)),这里的mean设置平均值,std设置方差
当只有一个mean值和一个std值的时候,只产生一个张量值
(2)
torch.rand()在区间[0,1]上生成服从均匀分布的张量。
A=torch.rand(3,4)
torch.rand_like(A)可以根据其他张量的维度生成一个随机张量(和上面的一样)
(3)
torch.randn(3,3)和torch.randn_like(A)生成服从标准正态分布的随机数张量。
import torch
A=torch.randn(3,3)
print(A)
B=torch.randn_like(A)
print(B)
A=torch.randperm(10)生成乱序的0~9
5、tensor.arange(start=0, end=10 ,step =2)
设置开始、结束、步长
torch.linspace(start=0,end=10,steps=5)
设置分为几个区间 steps
torch.logspace(start=0.1,end=1.0,steps=5)和linspace等价
4、张量的操作
1、改变张量的形状:
(1)tensor.reshape()可以用来创造张量
A=torch.arange(12.0).reshape(3,4)
(2)改变A张量的形状。
B =torch.reshape(input=A,shape=(2,-1))
A.resize(2,6)
(3)将B的形状赋给AA.resize_as(B)
2、改变维度
torch.unsqueeze()在张量指定维度上插入新的维度得到维度提升的张量。
import torch
A=torch.arange(12.0).reshape(2,6)
print(A.shape)
B=torch.unsqueeze(A,dim=0)
print(B.shape)
C=B.unsqueeze(dim=3)
print("C.shape=",C.shape)
#torch.Size([2, 6])
#torch.Size([1, 2, 6])
#C.shape= torch.Size([1, 2, 6, 1])
在这里的dim是列表的下标,0.1.2.3…
torch.squeeze()移除指定的或则所有维度大小是1的维度
去掉了所有维度大小是1的维度,因为维度是1,在某种意义上就是在拼凑维度(没有意义)
D=torch.squeeze(C)
print(D.shape)
#torch.Size([2, 6])
去掉了【0】上的维度
E=torch.squeeze(C,dim=0)
print(E.shape)
#torch.Size([2, 6, 1])
3、expand增加维度
(1)A.expand(n,m)对维度进行扩充到n*m,如果是(m,-1),-1表示不变或则随着m的调整而调整。
import torch
A=torch.arange(3)
print(A)
B=A.expand(3,-1)
print(B)
#tensor([[0, 1, 2])
#tensor([[0, 1, 2],
[0, 1, 2],
[0, 1, 2]])
(2)A.expand_as© A按照C的张量形状进行扩充。
4、通过.repeat()来扩展张量
>>> a.repeat(1,1).size() # 原始值:torch.Size([33, 55])
torch.Size([33, 55])
>>>
>>> a.repeat(2,1).size() # 原始值:torch.Size([33, 55])
torch.Size([66, 55])
>>>
>>> a.repeat(1,2).size() # 原始值:torch.Size([33, 55])
torch.Size([33, 110])
>>>
>>> a.repeat(1,1,1).size() # 原始值:torch.Size([33, 55])
torch.Size([1, 33, 55])
>>>
>>> a.repeat(2,1,1).size() # 原始值:torch.Size([33, 55])
torch.Size([2, 33, 55])
>>>
>>> a.repeat(1,2,1).size() # 原始值:torch.Size([33, 55])
torch.Size([1, 66, 55])
>>>
>>> a.repeat(1,1,2).size() # 原始值:torch.Size([33, 55])
torch.Size([1, 33, 110])
>>>
>>> a.repeat(1,1,1,1).size() # 原始值:torch.Size([33, 55]) ,这里的(1,1...)多出来的两个放在前面的维度
torch.Size([1, 1, 33, 55])
>>>
>>> # ------------------ 割割 ------------------
>>> # repeat()的参数的个数,不能少于被操作的张量的维度的个数
5、像列表那样取tensor中的元素
import torch
A=torch.arange(12).reshape(1,3,4)
print(A)
print(A[0])
print(A[0,0:2,])
print(A[0,-1,-4:-1])
输出:
tensor([[[ 0, 1, 2, 3],
[ 4, 5, 6, 7],
[ 8, 9, 10, 11]]])
tensor([[ 0, 1, 2, 3],
[ 4, 5, 6, 7],
[ 8, 9, 10, 11]])
tensor([[0, 1, 2, 3],
[4, 5, 6, 7]])
tensor([ 8, 9, 10])
6、根据条件筛选tensor中的元素
where这里就是一个三目运算符,如果为真则C=A,如果为假C=B。是针对tensor中的每一项元素来说的,而不是单纯C=A
import torch
A=torch.arange(12).reshape(1,3,4)
print(A)
B=-A
C=torch.where(5<A,A,B)
print(C)
输出:
tensor([[[ 0, 1, 2, 3],
[ 4, 5, 6, 7],
[ 8, 9, 10, 11]]])
tensor([[[ 0, -1, -2, -3],
[-4, -5, 6, 7],
[ 8, 9, 10, 11]]])
7、取torch的三角
torch.tril()表示取下三角部分,diagonal=0表示正常取,=1则向右平移一位。
import torch
A=torch.arange(12).reshape(1,3,4)
B=torch.tril(A,diagonal=0)
print(B)
C=torch.tril(A,diagonal=1)
print(C)
输出:
tensor([[[ 0, 0, 0, 0],
[ 4, 5, 0, 0],
[ 8, 9, 10, 0]]])
tensor([[[ 0, 1, 0, 0],
[ 4, 5, 6, 0],
[ 8, 9, 10, 11]]])
torch.triu()取函数的上三角部分。
torch.diag()取函数的对角线元素。
8、对tonsor进行拼接:
(1)tensor.cat()表示进行拼接,其中dim表示在那个维度进行拼接。
import torch
A=torch.arange(6.0).reshape(2,3)
print(A)
B=torch.linspace(0,10,6).reshape(2,3)
print(B)
C=torch.cat((A,B),dim=0)
print(C)
print(C.size())
输出:
tensor([[0., 1., 2.],
[3., 4., 5.]])
tensor([[ 0., 2., 4.],
[ 6., 8., 10.]])
tensor([[ 0., 1., 2.],
[ 3., 4., 5.],
[ 0., 2., 4.],
[ 6., 8., 10.]])
torch.Size([4, 3])
还可以在()里面对tensor进行操作(就和列表操作一样)进行多项拼接。
E=torch.cat((A[:,0:2],A,B),dim=1)
print(E)
print(E.size())
输出:tensor([[ 0., 1., 0., 1., 2., 0., 2., 4.],
[ 3., 4., 3., 4., 5., 6., 8., 10.]])
torch.Size([2, 8])
(2)torch.stack((A,B),dim=0)在新的维度进行拼接。dim=指定新的维度。
import torch
A=torch.arange(6.0).reshape(2,3)
print(A)
B=torch.linspace(0,10,6).reshape(2,3)
print(B)
C=torch.stack((A,B),dim=0)
print(C)
print(C.size())
输出:
tensor([[0., 1., 2.],
[3., 4., 5.]])
tensor([[ 0., 2., 4.],
[ 6., 8., 10.]])
tensor([[[ 0., 1., 2.],
[ 3., 4., 5.]],
[[ 0., 2., 4.],
[ 6., 8., 10.]]])
torch.Size([2, 2, 3])
(3)torch.chunk(E,2,dim=0)指定对谁进行拆分,拆分成几份,在那个维度进行拆分。
F=torch.chunk(E,2,dim=0)
print(F)
输出:
tensor([[ 0., 1., 0., 1., 2., 0., 2., 4.],
[ 3., 4., 3., 4., 5., 6., 8., 10.]])
torch.Size([2, 8])
(tensor([[0., 1., 0., 1., 2., 0., 2., 4.]]), tensor([[ 3., 4., 3., 4., 5., 6., 8., 10.]]))这是一个元组
(4)torch.split(E,[3,2,3],dim=1)指定对谁在那个维度进行怎么分,
E1,E2,E3=torch.split(E,[3,2,3],dim=1)
print(E1)
print(E2)
print(E3)
输出:
tensor([[ 0., 1., 0., 1., 2., 0., 2., 4.],
[ 3., 4., 3., 4., 5., 6., 8., 10.]])
torch.Size([2, 8])
tensor([[0., 1., 0.],
[3., 4., 3.]])
tensor([[1., 2.],
[4., 5.]])
tensor([[ 0., 2., 4.],
[ 6., 8., 10.]])