📜  并行化 Numpy 向量操作

📅  最后修改于: 2022-05-13 01:54:24.386000             🧑  作者: Mango

并行化 Numpy 向量操作

NumPy 是一个包含多维数组对象以及数组处理例程集合的库。正如您可能知道的那样,它不是并行操作,但是并行执行操作可以为我们提供很大的性能优势。我们将使用numexpr库来并行化 NumPy 操作。

数值表达式

NumExpr 是 NumPy 的快速数值表达式求值器。作用于数组的表达式,例如3*a+4*b (其中 a 和 b 是数组),与在Python中执行时相比,被加速并使用更少的内存。此外,它的多线程功能可以利用所有内核,与 NumPy 相比,可显着提高性能。

根据我们的需要,我们将使用 numexpr 包中的评估函数。

示例 1:

在这个例子中,我只使用了评估函数的ex参数来执行 a 和 b 之间的加法。

Python3
import numpy as np
import numexpr as ne
  
a = np.array([[6, 6], [0, 7]])
b = np.array([[19, 17], [13, 19]])
  
print(ne.evaluate('a+b'))


Python3
import numpy as np
import numexpr as ne
  
a = np.array([[6, 6], [0, 7]])
b = np.array([[19, 17], [13, 19]])
  
print(ne.evaluate('c+d', local_dict={'c': a, 'd': b}))


Python3
import numpy as np
import numexpr as ne
  
a = np.array([[6, 6], [0, 7]])
  
def calc():
    b = np.array([[19, 17], [13, 19]])
    out = np.zeros((2, 2))
    ne.evaluate('c+d', local_dict={'c': b},
                global_dict={'d': a}, out=out)
    print(out)
  
calc()


Python3
import numpy as np
import numexpr as ne
  
a = np.arange(1000000)
b = np.arange(1000000)
  
timeit np.add(np.multiply(2, a), np.multiply(4, b))
timeit ne.evaluate('2*a+4*b')


Python3
import numpy as np
import numexpr as ne
  
a = np.arange(1000000)
  
timeit np.sin(a)
timeit ne.evaluate('sin(a)')


Python3
import numpy as np
import numexpr as ne
  
a = np.random.randint(0, 1000, size=(10000, 10))
  
timeit np.cos(a)
timeit ne.evaluate('cos(a)')


输出:

[[25. 23.]
[13. 26.]]

示例 2:

在此示例中,我使用local_dict参数和 ex 来从本地范围传递 c 和 d 的操作数。

Python3

import numpy as np
import numexpr as ne
  
a = np.array([[6, 6], [0, 7]])
b = np.array([[19, 17], [13, 19]])
  
print(ne.evaluate('c+d', local_dict={'c': a, 'd': b}))

输出:

[[25. 23.]
[13. 26.]]

示例 3:

在此示例中,我使用global_dict参数为 d 传递操作数,而 local_dict 参数在 ex 参数中为 c 传递操作数。

Python3

import numpy as np
import numexpr as ne
  
a = np.array([[6, 6], [0, 7]])
  
def calc():
    b = np.array([[19, 17], [13, 19]])
    out = np.zeros((2, 2))
    ne.evaluate('c+d', local_dict={'c': b},
                global_dict={'d': a}, out=out)
    print(out)
  
calc()

输出:

[[25. 23.]
[13. 26.]]

比较性能

现在,让我们现在对我们的学习进行测试。在以下示例中,我们将使用 NumPy 和 NumExpr 执行相同的操作,并使用timeit对它们进行计时。

示例 1:

我们将执行一个简单的代数表达式,涉及对两行向量进行加法和乘法运算,每个向量的大小为 1000000。为此,我们使用了 NumPy 包中的加法乘法函数,并从 NumExpr 中求值来模拟它。

Python3

import numpy as np
import numexpr as ne
  
a = np.arange(1000000)
b = np.arange(1000000)
  
timeit np.add(np.multiply(2, a), np.multiply(4, b))
timeit ne.evaluate('2*a+4*b')

输出:

输出

输出

示例 2:

在此示例中,我们将使用 NumPy 库中的sin函数,并使用 NumExpr 的对应函数在 1000000 大小的行向量上评估函数。

Python3

import numpy as np
import numexpr as ne
  
a = np.arange(1000000)
  
timeit np.sin(a)
timeit ne.evaluate('sin(a)')

输出:

输出

输出

示例 3:

在这个例子中,我们将使用 NumPy 库中的cos函数,以及在 (10000, 10) 大小的矩阵上使用 NumExpr 的评估函数的对应函数。

Python3

import numpy as np
import numexpr as ne
  
a = np.random.randint(0, 1000, size=(10000, 10))
  
timeit np.cos(a)
timeit ne.evaluate('cos(a)')

输出:

输出

输出