基本数据:Tensor

基本数据:Tensor

Tensor,即张量,是PyTorch中的基本操作对象,可以看成是包含单一数据类型元素的多维矩阵。

一、Tensor数据类型

  1. 定义:Tensor在使用时可以有不同的数据类型,官方给出了7种CPU Tensor类型和8种GPU Tensor类型,在使用时可以根据网络模型所需要的精度与显存容量,合理选取。

  2. torch.set_default_tensor_type():设置默认使用的Tensor类型。

    torch.set_default_tensor_type('torch.DoubleTensor')
    
  3. Tensor之间类型转换:通过type(new_type)、type_as()、int()等多种方法操作

    import torch
    torch.set_default_tensor_type('torch.FloatTensor')
    a = torch.Tensor(2,2)
    print(a)
    # 使用double()转换
    b = a.double()
    print(b)
    # 使用type()
    c = a.type(torch.DoubleTensor)
    print(c)
    # 使用type_as()
    d = a.type_as(b)
    print(b)
    

二、Tensor的创建与维度查看

  1. Tensor的创建有多种方法

    import torch
    # 最基础的Tensor()函数创建方法
    a = torch.Tensor(2,2)
    print(a)
    # 使用Python的list序列进行创建
    b = torch.Tensor([[1, 2], [3, 4]])
    print(b)
    # 使用zeros()函数,所有元素均为0,类似的有ones()
    c = torch.zeros(2, 2)
    print(c)
    # 使用eye()函数,对角线均为1,不要求行列数相同,生成二维矩阵
    d = torch.eye(2, 2)
    print(b)
    # 使用randn()函数,生成随机矩阵
    e = torch.randn(2, 2)
    print(e)
    # 使用arange(start,end,step)函数,表示从start到end,间距为step的一维向量
    f = torch.arange(1, 6, 2)
    print(f)
    # 使用linspace(start,end,steps)函数,表示从stat到end,一个steps份的一维向量
    g = torch.linspace(1, 7, 3)
    print(g)
    # 使用randperm(num)函数,生成长度为num的随机排列向量
    h = torch.randperm(10)
    print(h)
    

    输出:

    tensor([[-1.8399e+19,  4.5909e-41],
            [-1.8399e+19,  4.5909e-41]])
    tensor([[1., 2.],
            [3., 4.]])
    tensor([[0., 0.],
            [0., 0.]])
    tensor([[1., 2.],
            [3., 4.]])
    tensor([[4.2157e-04, 8.0940e-01],
            [5.4407e-01, 7.1835e-01]])
    tensor([1, 3, 5])
    tensor([1., 4., 7.])
    tensor([6, 3, 1, 0, 8, 9, 2, 4, 7, 5])
    
  2. 使用Tansor.shape或者size()函数查看每一维的大小,两者等价

    import torch
    a = torch.Tensor(2, 2)
    print(a)
    print(a.shape)
    print(a.size())
    

    输出:

    tensor([[1.4013e-45, 0.0000e+00],
            [0.0000e+00, 0.0000e+00]])
    torch.Size([2, 2])
    torch.Size([2, 2])
    
  3. 查看Tensor的元素个数,使用Tensor.numel()或者Tensor.nelement()函数,两者等价

三、Tensor的组合与分块

  1. 组合操作是指将不同的Tensor叠起来,主要有Tensor.cat()和Tensor,stack()两个函数;

    import torch
    a = torch.Tensor([[1, 2], [3, 4]])
    print(a)
    b = torch.Tensor([[5, 6], [7, 8]])
    print(b)
    # 以第一维进行拼接,变成4x2的矩阵
    print(torch.cat([a, b], 0))
    # 以第二维进行拼接,变成2x4的矩阵
    print(torch.cat([a, b], 1))
    

    输出:

    tensor([[1., 2.],
            [3., 4.]])
    tensor([[5., 6.],
            [7., 8.]])
    tensor([[1., 2.],
            [3., 4.],
            [5., 6.],
            [7., 8.]])
    tensor([[1., 2., 5., 6.],
            [3., 4., 7., 8.]])
    
  2. 分块操作与组合操作相反,指将Tensor分割成不同 子Tensor,主要有tensor.chunk()与tensor.split()两个函数;

    import torch
    a = torch.Tensor([[1, 2, 3], [4, 5, 6]])
    print(a)
    # 使用chunk,沿0维进行分块,一共分两块,因此分割为1x3的Tesnsor
    print(torch.chunk(a, 2, 0))
    # 沿1维进行,分割成两个Tensor,当不能整除的时候,最后一个的维数会小于前面的
    # 因此,分割成2x2和2x1的两个矩阵
    print(torch.chunk(a, 2, 1))
    # 使用split,沿着第0维,每一维度为2,由于第1维的维度为2,因此相当于没有分割
    print(torch.split(a, 2, 0))
    # 使用split,沿着第1维,每一维度为2,分割成2x2和2x1的两个矩阵
    print(torch.split(a, 2, 1))
    

    输出:

    tensor([[1., 2., 3.],
            [4., 5., 6.]])
    (tensor([[1., 2., 3.]]), tensor([[4., 5., 6.]]))
    (tensor([[1., 2.],
            [4., 5.]]), tensor([[3.],
            [6.]]))
    (tensor([[1., 2., 3.],
            [4., 5., 6.]]),)
    (tensor([[1., 2.],
            [4., 5.]]), tensor([[3.],
            [6.]]))
    

四、Tensor的索引

  1. 索引主要包括下标索引、表达式索引,使用torch.where()和Tensor.clamp()的选择性索引。

  2. 下标索引和表达式索引

    import torch
    a = torch.Tensor([[0, 1], [2, 3]])
    print(a)
    # 根据下标进行索引
    print(a[1])
    print(a[0, 1])
    # 选择a中大于0的元素,返回和a相同大小的Tensor,符合条件的置1,否则置0
    print(a > 0)
    # 选择非0座标,并返回
    print(torch.nonzero(a))
    
    

    输出:

    tensor([[0., 1.],
            [2., 3.]])
    tensor([2., 3.])
    tensor(1.)
    tensor([[False,  True],
            [ True,  True]])
    tensor([[0, 1],
            [1, 0],
            [1, 1]])
    
    
  3. torch.where()和Tensor.clamp()

    import torch
    a = torch.Tensor([[0, 1], [2, 3]])
    print(a)
    # torch.where(condition, x, y),满足condition的位置输出x,否则输出y
    print(torch.where(a > 1, torch.full_like(a, 1), a))
    # 对Tensor元素进行限制可以使用clamp()函数,示例如下,限制最小值为1,最大值为2
    print(a.clamp(1, 2))
    

    输出:

    tensor([[0., 1.],
            [2., 3.]])
    tensor([[0., 1.],
            [1., 1.]])
    tensor([[1., 1.],
            [2., 2.]])
    

五、Tensor的变形

  1. 变形操作是指改变Tensor的维度,以适应在深度学习的计算中,数据维度经常变换的需求。在PyTorch中主要有4类不同的变形方法。

  2. view()、resize()和reshape()函数:可以在不改变Tensor数据的前提下任意改变Tensor的形状,必须保证调整前后的元素个数相同,并且调整前后共享内存,三者的作用基本相同。

    import torch
    a = torch.arange(1, 5)
    print(a)
    # 使用view()
    print(a.view(2, 2))
    # 使用resize_()
    print(a.resize_(4, 1))
    # 使用reshape()
    print(a.reshape(1, 4))
    

    输出:

    tensor([1, 2, 3, 4])
    tensor([[1, 2],
            [3, 4]])
    tensor([[1],
            [2],
            [3],
            [4]])
    tensor([[1, 2, 3, 4]])
    
  3. transpose()和permute()函数:transpose()函数可以将指定的两个维度的元素进行转置, permute()函数则可以按照给定的维度进行变换。

    import torch
    a = torch.randn(2, 2, 2)
    print(a)
    # 将0维和1维的元素进行转置
    print(a.transpose(0, 1))
    # 按照2、1、0的维度顺序重新进行元素排列
    print(a.permute(2, 1, 0))
    

    输出:

    tensor([[[-1.5178,  0.9670],
             [ 0.4453, -1.0351]],
            [[-0.1473,  0.1650],
             [-0.1403,  0.0548]]])
    tensor([[[-1.5178,  0.9670],
             [-0.1473,  0.1650]],
            [[ 0.4453, -1.0351],
             [-0.1403,  0.0548]]])
    tensor([[[-1.5178, -0.1473],
             [ 0.4453, -0.1403]],
            [[ 0.9670,  0.1650],
             [-1.0351,  0.0548]]])
    
  4. squeeze()和unsqueeze()函数:在实际应用中,经常需要增加或减少Tensor的维度。前者用于去除size为1的维度,而后者则是将指定的维度size变为1。

    import torch
    a = torch.arange(1, 4)
    print(a)
    print(a.shape)
    print(a.unsqueeze(0))
    print(a.unsqueeze(0).shape)
    print(a.unsqueeze(0).squeeze(0))
    print(a.unsqueeze(0).squeeze(0).shape)
    

    输出:

    tensor([1, 2, 3])
    torch.Size([3])
    tensor([[1, 2, 3]])
    torch.Size([1, 3])
    tensor([1, 2, 3])
    torch.Size([3])
    
    1. expand()和expand_as()函数:有时候需要采用复制的形式来扩展Tensor的维度,expand()函数将size为1的维度扩展为指定大小,也可以使用expand_as()函数指定。
    import torch
    a = torch.randn(2, 2, 1)
    print(a)
    # 将第2维的维度由1变为3,则复制该维的元素,并扩展为3
    print(a.expand(2, 2, 3))
    

    输出:

    tensor([[[ 0.5300],
             [ 0.8920]],
            [[-0.2896],
             [-0.2523]]])
    tensor([[[ 0.5300,  0.5300,  0.5300],
             [ 0.8920,  0.8920,  0.8920]],
            [[-0.2896, -0.2896, -0.2896],
             [-0.2523, -0.2523, -0.2523]]])
    
    
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章