Numba介绍
1 | Cython毕竟不是原生的 Python 代码,使用起来还是有诸多不便的。为此,numba 就成了一个功能强大又容易上手的替代选择,是一个用于编译python数组和数值计算函数的编译器,在使用NumPy数组和循环的代码上效果最佳 |
适用情景
1 | 使用numpy数组做大量科学计算时 |
Numba的装饰器
1 |
|
#####jit1
2
3
4
5
6
7
8
9
10
11
12
13#斐波那契数列
import time
from numba import jit
def fib(n):
if n<=2 :
return 1;
else:
return fib(n-1)+fib(n-2);
start = time.time()
fib(40)
end = time.time()
print("python3+numba cost_seconds:", end-start)
#####generated_jit
1 | import numpy as np |
#####vectorize和guvectorize(矢量化计算)
1 | vectorize和guvectorize,Numba可以将纯Python函数编译为一个ufunc |
######直接传矩阵会报错
1 | import numpy |
jit也无法使用
1 | import numpy |
######使用vectorize后会使函数转换成numpy中的unfunc,作用于每一个元素
1 | import numpy |
######guvectorize1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27import timeit
import numpy as np
from numba import jit, guvectorize
def row_sum_gu(input, output) :
output[0] = np.sum(input)
def row_sum_jit(input_array, output_array) :
m, n = input_array.shape
for i in range(m) :
output_array[i] = np.sum(input_array[i,:])
rows = int(64)
columns = int(1e6)
input_array = np.ones((rows, columns))
output_array = np.zeros((rows))
output_array2 = np.zeros((rows))
#the first run includes the compile time
row_sum_jit(input_array, output_array)
row_sum_gu(input_array, output_array2)
#run each function 100 times and record the time
print("jit time:", timeit.timeit("row_sum_jit(input_array, output_array)", "from __main__ import row_sum_jit, input_array, output_array", number=100))
print("guvectorize time:", timeit.timeit("row_sum_gu(input_array, output_array2)", "from __main__ import row_sum_gu, input_array, output_array2", number=100))
######
#####Numba中的数据类型
1 | 整形 Integer |
Numba的两种模式Nopython和Object模式
1 | Numba @jit装饰器从根本上以两种编译模式运行,nopython模式和object模式。 |
案例1:斐波那契数列
Numba无法理解Pandas,因此Numba只需通过解释器运行此代码,但会增加Numba内部开销
1 | #下面代码运行良好 |
故障排除和技巧
http://numba.pydata.org/numba-doc/latest/user/troubleshoot.html#numba-troubleshooting
弃用警告
1 | Numba弃用了列表和集合 |
Numba无法编译原因
1 | 1.普遍的原因是依赖了不受支持的Python功能 |
Numba编译太慢的原因
1 | 编译JIT函数缓慢的最常见原因是,在nopython模式下编译失败,并且Numba编译器已退回到对象模式。 与常规的Python解释相比,对象模式目前几乎没有提供任何加速,其主要点是允许进行称为循环提升的内部优化 :无论哪种代码包围这些内部循环,此优化都将允许以nopython模式编译内部循环 |
Numba中的cuda(大规模并行运算)———>了解有这个用法
1 | CUDA: 一种通用并行计算架构,架构使GPU能够解决复杂的计算问题.(CPU与GPU"协同处理") |
注意
1 | 注意:numba装饰的函数在第一次调用的时候会进行编译,会消耗一些时间,再次调用就不会了 |
swifter =========>优化apply,df.swifter.apply