1.利用数组进行数据处理
import numpy as np
import matplotlib.pyplot as plt
points=np.arange(-5,5,0.01)
xs,ys=np.meshgrid(points,points)
print xs
print ys
z=np.sqrt(xs**2+ys**2)
print z
plt.imshow(z,cmap=plt.cm.gray)
plt.colorbar()
plt.title("Image plot of $\sqrt{x^2+y^2}$ for a grid of values")
结果为:
[[-5. -4.99 -4.98 ..., 4.97 4.98 4.99]
[-5. -4.99 -4.98 ..., 4.97 4.98 4.99]
[-5. -4.99 -4.98 ..., 4.97 4.98 4.99]
...,
[-5. -4.99 -4.98 ..., 4.97 4.98 4.99]
[-5. -4.99 -4.98 ..., 4.97 4.98 4.99]
[-5. -4.99 -4.98 ..., 4.97 4.98 4.99]]
[[-5. -5. -5. ..., -5. -5. -5. ]
[-4.99 -4.99 -4.99 ..., -4.99 -4.99 -4.99]
[-4.98 -4.98 -4.98 ..., -4.98 -4.98 -4.98]
...,
[ 4.97 4.97 4.97 ..., 4.97 4.97 4.97]
[ 4.98 4.98 4.98 ..., 4.98 4.98 4.98]
[ 4.99 4.99 4.99 ..., 4.99 4.99 4.99]]
[[ 7.07106781 7.06400028 7.05693985 ..., 7.04988652 7.05693985
7.06400028]
[ 7.06400028 7.05692568 7.04985815 ..., 7.04279774 7.04985815
7.05692568]
[ 7.05693985 7.04985815 7.04278354 ..., 7.03571603 7.04278354
7.04985815]
...,
[ 7.04988652 7.04279774 7.03571603 ..., 7.0286414 7.03571603
7.04279774]
[ 7.05693985 7.04985815 7.04278354 ..., 7.03571603 7.04278354
7.04985815]
[ 7.06400028 7.05692568 7.04985815 ..., 7.04279774 7.04985815
7.05692568]]
2.将条件逻辑表述为数组运算
numpy.where函数时三元表达式x if condition else y的矢量化版本。
xarr=np.array([1.1,1.2,1.3,1.4,1.5])
yarr=np.array([2.1,2.2,2.3,2.4,2.5])
cond=np.array([True,False,True,True,False])
#当cond中的值为True时,选取xarr的值,否则从yarr中选取
result=[(x if c else y) for x,y,c in zip(xarr,yarr,cond)]
print result
结果为:
[1.1000000000000001, 2.2000000000000002, 1.3, 1.3999999999999999, 2.5]
有几个问题,第一它对数组处理的速度不是很快(因为所有的工作都是由纯Python完成的),第二无法用于多维数组;若使用np.where则可以将该功能写得非常简洁
result2=np.where(cond,xarr,yarr)
print result2
在数据分析工作中,where通常用于根据另一个数组而产生一个新的数组
arr1=np.random.randn(4,4)
print arr1
print np.where(arr1>0,2,-2)
#只将正值设置为2
print np.where(arr1>0,2,arr1)
结果为:
[[ 1.83291507 -1.58867214 0.90637336 1.02499554]
[ 0.86381994 -0.70843411 -1.16839393 0.55131969]
[-0.54296123 -1.13171815 0.29734885 0.91681327]
[-1.28282116 -1.32990481 0.10191195 0.78844874]]
[[ 2 -2 2 2]
[ 2 -2 -2 2]
[-2 -2 2 2]
[-2 -2 2 2]]
[[ 2. -1.58867214 2. 2. ]
[ 2. -0.70843411 -1.16839393 2. ]
[-0.54296123 -1.13171815 2. 2. ]
[-1.28282116 -1.32990481 2. 2. ]]
想象一下,我有两个布尔型数组cond1和cond2,希望根据4种不同的布尔值组合实现不同的赋值操作:
np.where(cond1 && cond2,0,np.where(cond1,1,np.where(cond2,2,3)))
3.数学和统计方法
arr2=np.random.randn(5,4)
print arr2
print arr2.mean()
print np.mean(arr2)
print arr2.sum()
#mean和sum这类的函数可以接受一个axis参数(用于计算该轴向上的统计值),最终结果是一个少一维的数组
print arr2.mean(axis=1)
print arr2.sum(0)
结果为:
[[ 0.04421807 0.05579019 0.49073741 1.83844835]
[-0.85086233 0.82695888 -1.17963151 0.61080947]
[ 1.6517786 0.64147281 0.39856902 1.58321548]
[ 0.09581811 0.855853 3.08102977 1.15668835]
[-1.66410818 -1.17020397 2.14328362 2.20244502]]
0.640615506991
0.640615506991
12.8123101398
[ 0.6072985 -0.14818138 1.06875898 1.29734731 0.37785412]
[-0.72315573 1.20987091 4.9339883 7.39160666]
其它如cumsum和cumprod之类的方法则不聚合,而是产生一个由中间结果组成的数组
arr3=np.array([[0,1,2],[3,4,5],[6,7,8]])
print arr3
print arr3.cumsum(0)
print arr3.cumprod(1)
结果为:
[[0 1 2]
[3 4 5]
[6 7 8]]
[[ 0 1 2]
[ 3 5 7]
[ 9 12 15]]
[[ 0 0 0]
[ 3 12 60]
[ 6 42 336]]
4.用于布尔型数组的方法
arr4=np.random.randn(100)
print (arr4>0).sum()
结果为:
41
另外两个方法any和all;any用于测试数组中是否存在一个或多个True,而all则检查数组中所有值是否都是True
bools=np.array([False,False,True,False])
print bools.any()
print bools.all()
结果为:
True
False
5.排序
arr5=np.random.randn(8)
print arr5
arr5.sort()
print arr5
结果为:
[-0.62678434 -1.05703028 -1.35622726 1.84139748 -1.38915508 0.75303163
0.75268662 0.95393155]
[-1.38915508 -1.35622726 -1.05703028 -0.62678434 0.75268662 0.75303163
0.95393155 1.84139748]
多维数组可以在任何一个轴上向上进行排序,只需将轴编号传给sort即可
arr6=np.random.randn(5,3)
print arr6
arr6.sort(1)
print arr6
结果为:
[[-2.83279139 0.37453421 -0.21970014]
[-1.06526559 -0.81824136 1.25382975]
[ 0.37518822 1.8481579 0.22969846]
[ 0.51275331 -0.58014161 0.90958922]
[-0.05234053 -0.82511264 1.04263001]]
[[-2.83279139 -0.21970014 0.37453421]
[-1.06526559 -0.81824136 1.25382975]
[ 0.22969846 0.37518822 1.8481579 ]
[-0.58014161 0.51275331 0.90958922]
[-0.82511264 -0.05234053 1.04263001]]
*方法np.sort返回的是数组的已排序副本,而就地排序则会修改数组本身。
6.唯一化以及其他的集合逻辑
numpy提供了一些针对一维ndarray的基本集合运算。最常用的可能要数np.unique了,它用于找出数组中唯一值并返回已排序的结果
names=np.array(['zhuheng','xiaoyang','zhuheng','benben','xiaoyang','zhuheng'])
print np.unique(names)
结果为:
['benben' 'xiaoyang' 'zhuheng']
另一个函数np.in1d用于测试一个数组中的值在另一个数组中的成员资格,返回一个布尔型数组
values=np.array([6,0,0,3,2,5,6])
print np.in1d(values,[2,3,6])
结果为:
[ True False False True True False True]
7.用于数组的文件输入输出
numpy能够读写磁盘上的文本数据或二进制数据
8.将数组以二进制格式保存到磁盘
np.save和np.load是读写磁盘数组数据的两个主要函数。默认情况下,数组是以未压缩的原始二进制格式保存在扩展名为.np的文件中的。
arr7=np.arange(10)
np.save('some_array',arr7)
print np.load('some_array.npy')
结果为:
[0 1 2 3 4 5 6 7 8 9]
通过np.savez可以将多个数组保存到一个压缩文件中,将数组以关键字参数的形式传入即可
np.savez('array_archive.npz',a=arr7,b=arr7)
arch=np.load('array_archive.npz')
print arch['b']
结果为:
[0 1 2 3 4 5 6 7 8 9]
8.存取文本文件
arr=np.loadtxt('array_ex.txt',delimiter=',')
print arr
9.线性代数
线性代数(如矩阵乘法,矩阵分解,行列式以及其他方阵数学等)是任何数组库的重要组成部分。numpy提供了一个用于矩阵乘法的dot函数
y=np.array([[6.,23.],[-1,7],[8,9]])
print x
print y
print x.dot(y)#相当于np.dot(x,y)
结果为:
[[ 1. 2. 3.]
[ 4. 5. 6.]]
[[ 6. 23.]
[ -1. 7.]
[ 8. 9.]]
[[ 28. 64.]
[ 67. 181.]]
分解为:
1*6+2*(-1)+3*8=28
1*23+2*7+3*9=64
4*6+5*(-1)+6*8=67
4*23+5*7+6*9=181
一个二维数组跟一个大小合适的一维数组的矩阵点积运算之后将会得到一个一维数组
numpy.linalg中有一组标准的矩阵分解运算以及诸如求逆和行列式之类的东西。
10.随机数生成
samples=np.random.normal(size=(4,4))
print samples
结果为:
[[-0.46232145 1.4761271 0.45452099 -0.29462295]
[ 0.43802714 -1.21157471 1.46811933 0.34658873]
[ 0.85083095 -0.71980021 0.82286834 -0.7895309 ]
[-0.20216229 -0.97692473 -1.67194947 2.00320505]]