PyTorch中torch.Tensor与torch.tensor的区别

根据网络上的资料,总结了一些PyTorch中torch.Tensor与torch.tensor的区别。

概要

过去写pytorch时只知道’torch.Tensor’生成的tensor的数据型为torch.float32,但是最近查阅了一些资料之后发现,torch.Tensortorch.tensor还是有一些其他区别的,本文就此进行一些总结。

理论差异

  1. torch.Tensor 是主要的张量类:在PyTorch中,torch.Tensor是主要的张量类,因此所有的张量实例都是torch.Tensor的实例。使用torch.Tensor()可以创建一个没有数据的空张量。此外,torch.Tensor的构造函数已经重载,因此它能实现torch.tensor和torch.empty的功能。

  2. torch.tensor 是返回张量的函数torch.tensor是一个函数,用于创建带有数据的张量。它的函数定义如下:

1
torch.tensor(data, dtype=None, device=None, requires_grad=False)  Tensor

空的tensor

  1. 若不提供数据直接调用torch.tensor(),会抛出错误,因为至少需要一个数据参数。
  2. 对于torch.Tensor,你可以不提供任何数据,例如torch.Tensor(),它会返回一个空的tensor。
  3. torch.tensor(0.)会返回一个值为0的tensor,但torch.Tensor(0.)会抛出一个错误。

实验:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
print(torch.tensor())
print(torch.tensor(0.))
print(torch.tensor(0.).dtype)
print(torch.tensor(()))
print(torch.tensor(()).dtype)
print(torch.Tensor(1))
print(torch.Tensor(1).dtype)
print(torch.Tensor(2))
print(torch.Tensor(2).dtype)
print(torch.Tensor(0.))

输出:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
TypeError: tensor() missing 1 required positional arguments: "data"
tensor(0.)
torch.float32
tensor([])
torch.float32
tensor([0.])
torch.float32
tensor([0., 0.])
torch.float32
TypeError: new(): data must be a sequence (got float)

数据类型

  1. torch.tensor()会从提供的数据中推断数据类型。
  2. torch.Tensor()默认创建一个与torch.get_default_dtype()返回值相同的数据类型的张量。

实验:

1
2
print(torch.Tensor([1, 2, 3]).dtype)
print(torch.tensor([1, 2, 3]).dtype)

输出:

1
2
torch.float32
torch.int64

效率

  1. 使用torch.Tensortorch.empty创建tensors时,它们的性能差异微小。
  2. 文章中提到"torch.Tensor is a favorite method used when creating parameters (for instance in nn.Linear, nn._ConvNd).Because it is very fast. It is even a bit faster than torch.empty().“但我还未做出验证:(

实验1:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
starttime = time.time()
for i in range(1000000):
    x = torch.Tensor(1)
endtime = time.time()
print(endtime - starttime)
starttime = time.time()
for i in range(1000000):
    x = torch.empty(1)
endtime = time.time()
print(endtime - starttime)

结果1:

1
2
1.7265019416809082
1.656996250152588

实验2:

1
2
3
4
5
6
import torch
torch.set_default_dtype(torch.float32) # default
%timeit torch.empty(1000,1000)
%timeit torch.Tensor(1000,1000)
%timeit torch.ones(1000,1000)
%timeit torch.tensor([[1]*1000]*1000)

结果2:

1
2
3
4
8.57 µs ± 123 ns per loop (mean ± std. dev. of 7 runs, 100,000 loops each)
8.45 µs ± 52 ns per loop (mean ± std. dev. of 7 runs, 100,000 loops each)
592 µs ± 5.48 µs per loop (mean ± std. dev. of 7 runs, 1,000 loops each)
100 ms ± 1.38 ms per loop (mean ± std. dev. of 7 runs, 10 loops each)

参考资料

torch.tensorとtorch.Tensor

What is the difference between torch.tensor and torch.Tensor?

Licensed under CC BY-NC-SA 4.0
comments powered by Disqus