PyTorch与向量化计算

还是先认错啊  只为自己好加标签 自己看方便~~ 

向量化计算是一种特殊的并行计算方式。程序在同一时间内只执行一个操作,而并行计算可以在同一时间内执行多个操作。向量化计算是指对不同的数据执行同样的一个或一批指令,或者把指令应用到一个数组或向量上,从而将多次循环操作变成一次计算。

向量化操作可以极大地提高科学运算的效率。尽管Python本身使用简便,但是其中存在着许多低效的操作,例如for循环等。因此,在科学计算中应当极力避免使用Python原生的for循环,尽量使用向量化数值运算,下面举例说明:

In: import torch as t    # 定义for循环完成加法操作    def for_loop_add(x, y):        result = []        for i, j in zip(x, y):            result.append(i + j)        return t.tensor(result)
    x = t.zeros(100)    y = t.ones(100)    %timeit -n 100 for_loop_add(x, y)    %timeit -n 100 (x + y) # +是向量化计算Out:100 loops, best of 3: 786 µs per loop    100 loops, best of 3: 2.57 µs per loop

从上面的例子中可以看出,for循环和向量化计算之间存在数百倍的速度差距,在实际使用中应该尽量调用内建函数(buildin-function)。这些函数底层由C/C++实现,在实现中使用了向量化计算的思想,通过底层优化实现了高效计算。在日常编程中应该养成向量化的编程习惯,避免对较大的Tensor进行逐元素的遍历操作,从而提高程序的运行效率。

这里主要从广播法则、高级索引两个方面介绍PyTorch中的向量化计算。 whaosoft aiot http://143ai.com

01

广播法则

广播法则(broadcast)是科学计算中经常使用的一个技巧,它在快速执行向量化计算的同时不会占用额外的内存/显存。NumPy中的广播法则定义如下。

  • 所有输入数组都与形状(shape)最大的数组看齐,形状不足的部分在前面加1补齐。

  • 两个数组要么在某一个维度的尺寸一致,要么其中一个数组在该维度的尺寸为1,否则不符合广播法则的要求。

  • 如果输入数组的某个维度的尺寸为1,那么计算时沿此维度复制扩充成目标的形状大小。

虽然PyTorch已经支持了自动广播法则,但是建议通过以下两种方式的组合手动实现广播法则,这样更加直观,也更不容易出错。

  • unsqueeze、view或者tensor[None] :为数据某一维度补1,实现第一个广播法则。

  • expand或者expand_as,重复数组,实现第三个广播法则;该操作不会复制整个数组,因此不会占用额外的空间。

注意:repeat可以实现与expand类似的功能,expand是在已经存在的Tensor上创建一个新的视图(view),repeat会将相同的数据复制多份,因此会占用额外的空间。

首先来看自动广播法则:

In: # 自动广播法则    # 第一步:a是2维的,b是3维的,所以先在较小的a前面补1个维度,    #       即:a.unsqueeze(0),a的形状变成(1,3,2),b的形状是(2,3,1),    # 第二步:a和b在第一和第三个维度的形状不一样,同时其中一个为1,    #       利用广播法则扩展,两个形状都变成了(2,3,2)    a = t.ones(3, 2)    b = t.zeros(2, 3, 1)    (a + b).shapeOut:torch.Size([2, 3, 2])

再来看如何手动实现以上广播过程:​​​​​​​

In: # 手动广播法则,下面两行操作是等效的,推荐使用None的方法    # a.view(1, 3, 2).expand(2, 3, 2) + b.expand(2, 3, 2)    a[None,:,:].expand(2, 3, 2) + b.expand(2, 3, 2)Out:tensor([[[1., 1.],             [1., 1.],             [1., 1.]],
             [[1., 1.],             [1., 1.],             [1., 1.]]])

02

索引操作

索引和切片是NumPy和PyTorch中的两种常用操作,本节将从基本索引入手,对比介绍高级索引的相关用法,帮助建立向量化思想。

2.1 基本索引

PyTorch中Tensor的索引和NumPy数组的索引类似,通过索引操作可以定位到数据的具体位置,也可以进行切片操作。基本索引有以下几种形式。

  • 元组序列:在索引中直接使用一个元组序列对Tensor中数据的具体位置进行定位,也可以直接使用多个整数(等价于元组序列省略括号的形式)代替。

  • 切片对象(Slice Object):在索引中常见的切片对象形如sta

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值