这是我参与2022首次更文挑战的第5天,活动详情查看:2022首次更文挑战
最近每天都谈一谈自己感想,可能是随着年龄增长,经历的也多了,有的时候总想啰嗦两句。这些年一直 focus 前端,也就是和顾客最接近层面,现在前端技术可以是日新月异,所以得紧跟其脚步,新的技术其绚丽 demo,通常会紧紧将我吸引住,让我夜不能寐,将其搞到手,还没等到应用,下一个又来了。
今天深度学习paper 也是如此,一路追赶,多少披星戴月。不过感觉自己还是停留在应用,也是处于整个体系前端,希望自己能够停下浮躁,跟风心里。也停下疲惫脚步。打打基础,毕竟先来看底层东西,虽然耗时,不过这些年看过来,变化不大,比较保值。
tensor 和 Tensor
data = np.array([1,2,3])
复制代码
torch.tensor
是一个工厂方法,返回一个 Tensor 类的实例torch.Tensor
是一个类,调用类来实例化一个 Tensor
torch.tensor(data) #tensor([1, 2, 3])
复制代码
接下来我们就用以下几种方法来解释一下如何基于 data 这个 numpy.ndarray 来创建一个 tensor
t1 = torch.Tensor(data)
t2 = torch.tensor(data)
t3 = torch.as_tensor(data)
t4 = torch.from_numpy(data)
复制代码
tensor([1., 2., 3.])
tensor([1, 2, 3])
tensor([1, 2, 3])
tensor([1, 2, 3])
复制代码
大家从输出结果可能已经看出了 Tensor
类型浮点型,而其他都是整型,为证实将他们类型输出一下。
print(t1.dtype)
print(t2.dtype)
print(t3.dtype)
print(t4.dtype)
复制代码
torch.float32
torch.int64
torch.int64
torch.int64
复制代码
这是因为 Tensor
采用默认指定数据类型作为类型,torch.get_default_dtype()
为 torch.float32
也可以在创建 torch.tensor
时候指定数据类型 print(torch.tensor(np.array([1.,2.,3.]),dtype=torch.float32))
tensor 类型
我们区分 tensor 主要从两个方面,一个是 tensor 的数据类型,有点编程经验,应该不难理解。tensor 作为容器,所以其类型是由其中放置数据类型所决定,在选择 tensor 数据类型,需要考虑数据精度要求,够用就好不要浪费。
t1 = torch.tensor([1,2,3])
t2 = torch.tensor([1.,2.,3.])
print(t1.dtype)
print(t2.dtype)
复制代码
torch.int64
torch.float32
复制代码
通过下面代码可以了解到 torch.Tensor
和 torch.tensor
是对数据进行 copy 而 torch.as_tensor
和 from_numpy
是对 numpy array 的对象共享内存。
data = np.array([1,2,3])
复制代码
t1 = torch.Tensor(data)
t2 = torch.tensor(data)
t3 = torch.as_tensor(data)
t4 = torch.from_numpy(data)
复制代码
data[0] = 0
data[1] = 0
data[2] = 0
复制代码
print(t1) #tensor([1., 2., 3.])
print(t2) # tensor([1, 2, 3])
复制代码
print(t3) #tensor([0, 0, 0])
print(t4) #tensor([0, 0, 0])
复制代码
- 由于
numpy.ndarray
对象是分配在 CPU 上,所以如果 torch 正在使用 GPU,在调用torch.as_tensor
时,就需要将数据从 CPU 复制到 GPU。 as_tensor
不支持 python 内置的列表结构数据,例如 list- 如果想要更好的使用
as_tensor
就需要开发人员对内存,否则可能不经意之间就修改底层数据,导致可能影响多个对象。 - 如果需要在 numpy.ndarray 对象和 tensor 对象之间来回切换,使用
as_tensor()
可以提升性能,如果只是进行一次加载,使用as_tensor
优势就不那么明显。
还有就是 tensor 根据其运行设备(device)不同而不同,所以下面例子介绍运行在 CPU 上 tensor 和运行在 GPU 上 tensor 是无法进行计算。
t1 + t2 #tensor([2., 4., 6.])
复制代码
t1 = torch.tensor([1,2,3])
t2 = t1.cuda()
复制代码
t1 + t2
复制代码
RuntimeError Traceback (most recent call last)
<ipython-input-4-9ac58c83af08> in <module>()
----> 1 t1 + t2
RuntimeError: Expected all tensors to be on the same device, but found at least two devices, cuda:0 and cpu!
复制代码
这里还有一点需要注意就是 reference 和 copy,虽然这些方法都可以得到一个我们想要 tensor,
batch = next(iter(train_loader))
复制代码
len(batch) #2
复制代码
type(batch) #list
复制代码
images,labels = batch
len(images) #10
复制代码
grid = torchvision.utils.make_grid(images,row=10)
plt.figure(figsize=(15,15))
plt.imshow(np.transpose(grid,(1,2,0)))
复制代码