ufunc是universal function的缩写,它是一种能对数组中每个元素进行操作的函数。Numpy内置的许多ufunc函数都是C语言实现的,计算速度非常快,简单看个例子:
上述代码中先用linspace( )产生一个从0到2*PI的等差数组,然后将其传给np.sin( )计算每个元素的正弦值。函数计算完成后,返回一个计算结果的数组。如果通过out参数指定计算结果的保存位置,则计算结果将保存在out参数中,如:
对于计算单个元素,则建议采用Math库里对应的函数,np.sin( )对应math.sin( ),因为对于np.sin( )为了实现数组计算,底层做了很多复杂的处理,因此对于单个元素,math库里的函数计算速度快得多;而对于数组元素,则采用numpy库里的函数计算。
在读取计算结果时,通过下标获取数组元素的类型为Numpy中定义的类型,将其转换为python的标准类型需耗时间。针对此问题,可以采用数组提供的item( )方法,用来获取数组中单个元素,并直接返回标准的python数据类型,如:
一、数组的四则运算
二、比较和布尔运算
使用“==”、“>”等比较运算符比较两个数组,将返回一个布尔数组,它的每个元素的值是两个数组对应元素比较的结果,如:
由于Python的布尔运算使用and,or和Not等关键字,无法被重载,因此数组的布尔运算智能通过ufunc对应的函数来操作,这些函数以"logical_"开头,如下:
以“bitwise_"开头的函数是比特运算函数,包括bitwise_and、bitwise_not、bitwise_or和bitwise_xor等,也可以使用&、~、|、^等操作符来计算。对于布尔数组来说,位运算和布尔运算的结果相同,但是位运算符的优先级高于比较运算符。
自定义ufunc函数
通过Numpy提供的标准ufunc函数可以满足大多要求,但有些特殊情况需要自定义函数来实现。这时,可以采用python来实现,然后使用frompyfunc( )函数将一个计算单个元素的函数转换为ufunc函数。例如,用一个分段函数来描述三角波,它的样子如图所示:
Python函数定义如下:
1)通过列表推导计算
先使用列表推导计算一个列表,然后用array( )转换为数组,这种方法每次都要使用列表推导,而且对于多维数组,比较复杂,计算如下:
2)fromnpyfunc( )函数计算
通过frompyfunc( )可以将计算单个值的函数转换为一个能对数组中每个元素计算的ufunc函数。frompyfunc( )的调用格式为:
其中,ufunc是计算单个元素的函数,nin是输入参数的个数,nout是func返回值的个数。如:
代码简洁高效。值得注意: triangle_wave_ufunc( )所返回数组的元素类型是object,因此还需要调用数组的astype()方法将其转换为双精度浮点数组:
3)vectorize( )函数计算
使用vectorize( )可以实现和frompyfunc( )类似的功能,但他可以通过otypes参数指定返回数组的元素类型。otypes参数可以是一个表示元素类型的字符串,也可以是一个类型列表,使用列表可以描述多个返回数组的元素类型,如将上面的代码改成vectorize( ),则为: