一、Numpy简介
Numpy是python的科学计算库,支持高级大量的维度数组与矩阵运算,此外有针对数组运算提供了大量的数学函数库。基本功能如下:
1、快速高效的多维数组对象ndarray;
2、用于对数组执行元素级计算以及 直接对数组执行数学运算的函数;
3、用于读写硬盘上基于数组的数据集的工具;
4、线性代数运算、傅里叶变换,以及随机数生成;
5、用于将c、c++、Fortran代码集成到Python的工具;
6、除了为Python提供快速的数组处理能力,NumPy在数据分析方面还有另外一个主要作用,即作为在算法之间传递数据的容器。
二、Numpy基础
1、创建数组
首先来看一下numpy数组创建函数
类型 | 说明 |
---|---|
array | 将输入数据(列表、元组、数组或其他序列类型)转换为ndarray,要么推断出dtype,要么显示指定dtype。默认直接复制输入数据 |
asarray | 将输入转换为darray,如果输入本身就是一个ndarray就不进行复制 |
arange | 类似于内置的range,但返回一个ndarray而不是列表 |
ones,ones_like | 根据指定形状和dtype创建一个全1数组。ones_like以另一个数组为参数,并根据其形状和dtype创建一个全1数组 |
zeros,zeros_like | 类似于ones和ones_like,只不过产生的是全0数组而已 |
empty,empty_like | 创建数组,只分配内容空间但不填充任何值 |
eye,identity | 创建一个正方的N*N单位矩阵 |
Numpy的ndarray数组和标量之间的运算
1、不用编写循环即可对数据执行批量运算
2、大小相等的数组之间的任何算术运算都会将运算应用到元素级
3、数组与标量的算术运算也会将那个标量值传播到各个元素
一维数组
import numpy as np
arr = np.array([[1,3,4],[5,7,9]])
print (arr * arr)
#输出结果
[[ 1 9 16]
[25 49 81]]
print(arr - arr)
#输出结果
[[0 0 0]
[0 0 0]]
print(1/arr)
#输出结果
[[1. 0.33333333 0.25 ]
[0.2 0.14285714 0.11111111]]
print(arr ** 0.5)
#输出结果
[[1. 1.73205081 2. ]
[2.23606798 2.64575131 3. ]]
二维数组
arr=np.array([[[1,2,3],[4,5,6]],[[7,8,9],[10,11,12]]])
print(arr[0])
#输出结果
[[1 2 3]
[4 5 6]]
print(arr[1,0])
#输出结果
[7 8 9]
values=arr[0]
values
#赋值结果
array([[1, 2, 3],
[4, 5, 6]])
#同上
values=arr[0].copy()
values
array([[1, 2, 3],
[4, 5, 6]])
arr[0]=1
arr[0]
#将第一行全部赋值为1
#输出结果
array([[1, 1, 1],
[1, 1, 1]])
arr[0]=values
arr[0]
#再赋值回来
array([[1, 2, 3],
[4, 5, 6]])
2、数据切片
arr=np.array([1,2,3,4,5,6,7,8,9,10])#一维数组
arr[1:6]#前闭后开,下标为1-5的数据(下标从0开始)
#输出结果
array([2, 3, 4, 5, 6])
arr=np.array([[1,2,3],[4,5,6],[7,8,9]])#二维数组
arr[:2]#前两行
#输出结果
array([[1, 2, 3],
[4, 5, 6]])
arr[:2,1:]#前两行的2、3两列
#输出结果
array([[2, 3],
[5, 6]])
arr[:,:1]#打印第一列的所有元素
#输出结果
array([[1],
[4],
[7]])
arr[:2,1:]=0#前两行的第2、3列设置为0
arr
#输出结果
array([[1, 0, 0],
[4, 0, 0],
[7, 8, 9]])
3、数据索引
Numpy的ndarray布尔型索引
1、布尔型数组的长度必须跟被索引的轴长度一致
2、可以将布尔型数组跟切片、整数(或整数序列)混合使用
例如
import numpy.random as np_random
name_arr = np.array(['Bob','Joe','Eill','Eill','Joe','Joe','Bob'])
rand_arr=np_random.randn(7,4)#随机7*4的数组
rand_arr
#输出结果
array([[ 0.52900587, 1.70244139, -1.35744235, 1.25015313],
[ 0.23373258, 1.09742228, -1.00995459, -1.54458745],
[-0.62998363, 0.11589576, 0.13457285, 0.31126254],
[-1.01457169, -0.06292203, -0.67612224, -0.74714611],
[-1.99870067, 1.53986087, -0.38757238, -1.08902317],
[ 1.09207708, -0.64661848, -0.07324105, 0.32222022],
[-1.2301582 , 1.76768207, -1.09098274, -0.47474178]])
name_arr=='Bob'#返回布尔数组,元素等于‘Bob’为True,否则Faluse
#输出结果
array([ True, False, False, False, False, False, True])
rand_arr[name_arr=='Bob']#利用布尔数组选择行,前提是长度必须等于数组行数
#输出结果(将符合条件的行输出)
array([[ 0.52900587, 1.70244139, -1.35744235, 1.25015313],
[-1.2301582 , 1.76768207, -1.09098274, -0.47474178]])
rand_arr[name_arr == 'Bob',:2]#增加限制打印列的范围
#输出结果
array([[ 0.52900587, 1.70244139],
[-1.2301582 , 1.76768207]])
rand_arr[~(name_arr == 'Bob')]#对布尔数组的内容取反
#输出结果
array([[ 0.23373258, 1.09742228, -1.00995459, -1.54458745],
[-0.62998363, 0.11589576, 0.13457285, 0.31126254],
[-1.01457169, -0.06292203, -0.67612224, -0.74714611],
[-1.99870067, 1.53986087, -0.38757238, -1.08902317],
[ 1.09207708, -0.64661848, -0.07324105, 0.32222022]])
mask_arr = (name_arr == 'Bob') | (name_arr == 'Eill')
rand_arr[mask_arr]
#输出结果
array([[ 0.52900587, 1.70244139, -1.35744235, 1.25015313],
[-0.62998363, 0.11589576, 0.13457285, 0.31126254],
[-1.01457169, -0.06292203, -0.67612224, -0.74714611],
[-1.2301582 , 1.76768207, -1.09098274, -0.47474178]])
rand_arr[name_arr !='Joe']=7
rand_arr
#输出结果
array([[ 7. , 7. , 7. , 7. ],
[ 0.23373258, 1.09742228, -1.00995459, -1.54458745],
[ 7. , 7. , 7. , 7. ],
[ 7. , 7. , 7. , 7. ],
[-1.99870067, 1.53986087, -0.38757238, -1.08902317],
[ 1.09207708, -0.64661848, -0.07324105, 0.32222022],
[ 7. , 7. , 7. , 7. ]])
Numpy的ndarray花式索引
1、花式索引是一个NumPy术语,它指的是利用整数数组进行索引
2、一次传入多个索引数组会有一点特别。它返回的是一个一维数组,其中的元素对应各个索引元组
import numpy as np
arr=np.empty((8,4))#empty创建的数组中,包含的均是无意义的数值
arr
#输出结果
array([[6.23060065e-307, 8.90104239e-307, 1.89150801e-307,
1.50202247e-307],
[3.56043053e-307, 7.56595733e-307, 3.56043054e-307,
7.56595733e-307],
[1.00131040e-307, 8.34426464e-308, 6.23038675e-307,
1.50201822e-307],
[3.56043053e-307, 1.60219306e-306, 2.44763557e-307,
1.69119330e-306],
[4.22805115e-307, 3.22651328e-307, 3.11524091e-307,
1.60219035e-306],
[4.45063154e-308, 6.23039354e-307, 2.33422937e-312,
2.67023123e-307],
[1.61324985e-307, 3.22649121e-307, 5.34041153e-307,
2.00264456e-307],
[8.34427737e-308, 1.50198257e-307, 4.22786442e-307,
2.00271247e-307]])
for i in range(8):
arr[i]=i
arr
#输出结果
array([[0., 0., 0., 0.],
[1., 1., 1., 1.],
[2., 2., 2., 2.],
[3., 3., 3., 3.],
[4., 4., 4., 4.],
[5., 5., 5., 5.],
[6., 6., 6., 6.],
[7., 7., 7., 7.]])
print(arr[[4,3,0,6]])
#输出结果
[[4. 4. 4. 4.]
[3. 3. 3. 3.]
[0. 0. 0. 0.]
[6. 6. 6. 6.]]
print(arr[[-3,-5,-7]])
#输出结果
[[5. 5. 5. 5.]
[3. 3. 3. 3.]
[1. 1. 1. 1.]]
arr=np.arange(32).reshape((8,4))#依次生成32个自然数,并且以8行4列的数组形式显示:
arr
#输出结果
array([[ 0, 1, 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, 27],
[28, 29, 30, 31]])
print(arr[[1,5,7,2],[0,3,1,2]])#自动匹配(1,0),(5,3),(7,1),(2,2)
#数据结果
[ 4 23 29 10]
print(arr[[1,5,7,2]][:,[0,3,1,2]])#1、5、7、2行的0、3、1、2列
#输出结果
[[ 4 7 5 6]
[20 23 21 22]
[28 31 29 30]
[ 8 11 9 10]]
print(arr[np.ix_([1,5,7,2],[0,3,1,2])])#可读性更好的写法
#能把两个一维数组 转换为 一个用于选取方形区域的索引器
#直接往np.ix_()里扔进两个一维数组[1,5,7,2],[0,3,1,2],就能先按我们要求选取行,再按顺序将列排序,跟上面得到的结果一样
#输出结果
[[ 4 7 5 6]
[20 23 21 22]
[28 31 29 30]
[ 8 11 9 10]]
4、NumPy的ndarray数组转置和轴对换
import numpy as np
import numpy.random as np_random
print ('转置矩阵')
arr=np.arange(15).reshape((3,5))#生成顺序数组,后整形为3行5列
print (arr)
#输出结果
转置矩阵
[[ 0 1 2 3 4]
[ 5 6 7 8 9]
[10 11 12 13 14]]
print(arr.T)
#输出结果
[[ 0 5 10]
[ 1 6 11]
[ 2 7 12]
[ 3 8 13]
[ 4 9 14]]
print('转置矩阵做点积')
arr = np_random.randn(6,3)
print(arr)
#输出结果
[[ 0.86578763 0.645244 -0.49405087]
[ 0.27238488 -0.40718433 -0.02145935]
[-1.96089557 -0.06565915 -0.09322006]
[ 0.73279045 -0.7511035 0.29078194]
[ 2.18427138 -0.86903329 0.57696171]
[-0.67968328 1.25416114 -0.05842028]]
print(np.dot(arr.T,arr))
#输出结果
转置矩阵做点积
[[10.43888587 -2.72455423 1.26223693]
[-2.72455423 3.4787455 -1.0969994 ]
[ 1.26223693 -1.0969994 0.67408863]]
print('高维矩阵转换')
arr=np.arange(16).reshape((2,2,4))
arr_copy=arr.copy()
print(arr)
#输出结果
[[[ 0 1 2 3]
[ 4 5 6 7]]
[[ 8 9 10 11]
[12 13 14 15]]]
print(arr[0])
#输出结果
[[0 1 2 3]
[4 5 6 7]]
print(arr[0][0])
#输出结果
[0 1 2 3]
print(arr[0][0][1])
#输出结果
1
print(arr.transpose(1,0,2))#transpose的参数为坐标,现在传入为(1,0,2)代表a[x][y][z]=a[y][x][z]
#输出结果
[[[ 0 1 2 3]
[ 8 9 10 11]]
[[ 4 5 6 7]
[12 13 14 15]]]
print(arr_copy)
#输出结果
print(arr_copy)
print(arr_copy)
[[[ 0 1 2 3]
[ 4 5 6 7]]
[[ 8 9 10 11]
[12 13 14 15]]]
print(arr_copy.transpose(0,2,1))
#输出结果
[[[ 0 4]
[ 1 5]
[ 2 6]
[ 3 7]]
[[ 8 12]
[ 9 13]
[10 14]
[11 15]]]
5、NumPy的ndarray快速的元素级数组函数
一元函数
类型 | 说明 |
---|---|
abs,fabs | 计算整数,浮点数或复数的绝对值。对于非复数值,可以使用更快的fabs |
sqrt | 计算各元素的平方根。相当于arr**0.5 |
sqare | 计算各元素的平方。相当于arr**2 |
exp | 计算各元素的e^x |
log,log10,log2,log1p | 分别为自然对数、底数为10的log、底数为2的log和log(1+x) |
sign | 计算各元素的正负号:1(正数)、0(零)、-1(负数) |
ceil | 计算各元素的ceiling值,即大于等于该值得最小整数 |
floor | 计算各元素的floor值,即小于等于该值得最大整数 |
rint | 将各元素值四舍五入到最接近的整数,保留dtype |
modf | 将数组的小数部分与整数部分以两个独立数组的形式返还 |
isnan | 返回一个表示“哪些值是NaN(这不是一个数字)”的布尔型数组 |
isfinite,isinf | 分别返回一个表示“哪些元素是有限的(非inf,非NaN)”或“哪些元素是无穷的”的布尔型数组 |
cos,cosh,sin,sinh,tan,tanh | 普通型或双曲型三角函数 |
arccos,arccosh,arcsin,arcsinh,arctan,arctanh | 反三角函数 |
logical_not | 计算各元素not x的真值。相当于-arr |
二元函数
类型 | 说明 |
---|---|
add | 将数组中对应的元素相加 |
subtract | 从第一个数组中减去第二个数组中的元素 |
multiply | 数组元素相乘 |
divide,floor_divide | 除法或向下取整除法 |
power | 对第一个数组中的元素A和第二个数组中对应位置的元素B,计算A^B |
maximum,fmax | 元素级的最大值计算。fmax将忽略NaN |
minimum,fmin | 元素级的最小值计算。fmin将忽略NaN |
mod | 元素级的求模计算 |
copysign | 将第二个数组中的符号复制给第一个数组中的值 |
greater,greater_equal,less,less_equal,equal,not_equal | 执行元素级的比较,最终产生布尔型数组 |
logical_and,logical_or,logical_xor | 执行元素级的真值逻辑运算,最终产生布尔型数组 |
举例说明
import numpy as np
import numpy.random as np_random
print('求平方根')
arr=np.arange(10)
print(np.sqrt(arr))
#输出结果
求平方根
[0. 1. 1.41421356 1.73205081 2. 2.23606798 2.44948974 2.64575131 2.82842712 3. ]
print('数组比较')
x=np_random.randn(8)#标准正态分布中返回一个或多个样本值,numpy.random.rand(d0, d1, …, dn)的随机样本位于[0, 1)中。
y=np_random.randn(8)
print(x)
print(y)
print (np.maximum(x,y))
#输出结果
数组比较
[ 9.52102078e-01 -5.50715978e-01 -2.88311757e-02 -6.73292894e-01
1.49144587e+00 -4.29510384e-01 -4.29998122e-01 -1.36136122e-03]
[ 2.13373561 2.06364166 0.61558615 -0.59547026 1.31034061 0.17616641
0.28403327 -0.26767038]
[ 2.13373561e+00 2.06364166e+00 6.15586151e-01 -5.95470255e-01
1.49144587e+00 1.76166407e-01 2.84033273e-01 -1.36136122e-03]
print('使用modf函数把浮点数分解成整数和小数部分')
arr=np_random.randn(7) * 5 #统一乘5
print(np.modf(arr))
#输出结果
使用modf函数把浮点数分解成整数和小数部分
(array([-0.82838311, -0.71882546, -0.41527595, -0.21803734, -0.99155683,
0.75074988, -0.35514585]), array([ -4., -1., -11., -3., -1., 1., -3.]))
6、利用数组进行数据处理
NumPy数组使你可以将许多种数据处理任务表述为简洁的数组表达式(否则需要编写循环)。将数组表达式代替循环的做法,通常被称为矢量化。矢量化数组运算要比等价的纯Python方式快上一两个数量级
print('通过真值表选择元素')
x_arr=np.array([1.1,1.2,1.3,1.4,1.5])
y_arr=np.array([2.1,2.2,2.3,2.4,2.5])
cond=np.array([True,False,True,True,False])
result=[(x if c else y) for x,y,c in zip(x_arr,y_arr,cond)]
print(result)
#输出结果
通过真值表选择元素
[1.1, 2.2, 1.3, 1.4, 2.5]
print(np.where(cond,x_arr,y_arr))
#输出结果
[1.1 2.2 1.3 1.4 2.5]
arr=np_random.randn(4,4)
print(arr)
print(np.where(arr>0,2,-2))
print(np.where(arr >0,2,arr))
#输出结果
[[-1.17689271 1.22467723 0.43345675 -0.72233803]
[-0.63662559 0.47394752 -0.78281055 0.7745087 ]
[ 0.34016053 1.2149215 -0.44530653 -2.02560303]
[ 0.42546874 1.21322415 -0.86223039 0.86367628]]
[[-2 2 2 -2]
[-2 2 -2 2]
[ 2 2 -2 -2]
[ 2 2 -2 2]]
[[-1.17689271 2. 2. -0.72233803]
[-0.63662559 2. -0.78281055 2. ]
[ 2. 2. -0.44530653 -2.02560303]
[ 2. 2. -0.86223039 2. ]]
cond_1=np.array([True,False,True,True,False])
cond_2=np.array([False,True,False,True,False])
# 传统代码
result=[]
for i in range(len(cond)):
if cond_1[i] and cond_2[i]: # 如果同时满足,就不在往下走
result.append(0)
elif cond_1[i]:
result.append(1)
elif cond_2[i]:
result.append(2)
else:
result.append(3)
print(result)
#输出结果
[1, 2, 1, 0, 3]
result = np.where(cond_1 & cond_2,0,np.where(cond_1,1,np.where(cond_2,2,3)))
print(result)
[1 2 1 0 3]
7、利用数组进行数据处理——数学和统计方法
类型 | 说明 |
---|---|
sum | 对数组中全部或某轴向的元素求和。零长度的数组的sum为0 |
mean | 算术平均数,零长度的数组的mean为NaN |
std,var | 分别为标准差和方差,自由度可调(默认为n) |
min,max | 最大值和最小值 |
argmin | 分别为最大值和最小值的索引 |
cumsum | 所有元素的累计和 |
cumprod | 所有元素的累计积 |
import numpy as np
import numpy.random as np_random
print('求和,求平均')
arr=np.random.randn(5,4)
print(arr)
print(arr.mean())
print(arr.sum())
print(arr.mean(axis=1))#对每一行的元素求平均值
print(arr.sum(0))#对每一列元素求和,axis可以省略
#输出结果
求和,求平均
[[ 1.1920312 0.59548133 -1.69638354 -0.86765064]
[ 0.48965205 1.21543697 -0.46861947 0.15786849]
[ 0.46646589 -1.07657886 0.34960628 -0.64421778]
[ 0.75182741 0.88173646 -2.1914321 0.53707905]
[ 0.2316153 1.01686933 1.52000011 -2.31109877]]
0.00748443502551317
0.1496887005102634
[-0.19413041 0.34858451 -0.22618112 -0.0051973 0.11434649]
[ 3.13159185 2.63294523 -2.48682873 -3.12801965]
print('cumsum和cumprod函数演示')
arr=np.array([[0,1,2],[3,4,5],[6,7,8]])
print(arr.cumsum(0))# 按列求和
print(arr.cumprod(1))# 按行求积
print(arr.cumprod(0))# 按列求积
#输出结果
cumsum和cumprod函数演示
[[ 0 1 2]
[ 3 5 7]
[ 9 12 15]]
[[ 0 0 0]
[ 3 12 60]
[ 6 42 336]]
[[ 0 1 2]
[ 0 4 10]
[ 0 28 80]]
print('对正数求和')
arr=np_random.randn(100)
print((arr > 0).sum())
#输出结果
对正数求和
42
print('对数组逻辑操作')
bools=np.array([False,False,True,False])
print(bools.any())# 有一个为True则返回True
print(bools.all())# 有一个为False则返回False
#输出结果
对数组逻辑操作
True
False
8、利用数组进行数据处理——排序
import numpy as np
import numpy.random as np_random
print('一维数组排序')
arr=np_random.randn(8)
arr.sort()
print(arr)
一维数组排序
[-1.93454221 -1.6182566 -0.77200267 -0.688614 -0.63448136 -0.6169222
-0.18656019 0.26607257]
print('二维数组排序')
arr=np_random.randn(5,3)
arr.sort(1) # 对每一行元素做排序
print(arr)
#输出结果
二维数组排序
[[-0.25145057 -0.01089318 0.19817363]
[-1.46680866 0.08178992 1.49258159]
[ 0.65733633 1.59214515 2.81517738]
[ 0.30385335 0.78703474 1.23996363]
[-0.82907411 -0.32716698 2.83399797]]
print('找位置在5%的数字')
large_arr=np_random.randn(1000)
large_arr.sort()
print(large_arr[int(0.05 * len(large_arr))])
#输出结果
找位置在5%的数字
-1.6407082885132667
9、利用数组进行数据处理——去重以及其他集合运算
类型 | 说明 |
---|---|
unique(x) | 计算x中的唯一元素,并返回有序结果 |
intersect1d(x,y) | 计算x和y的公共元素,并返回有序结果 |
union1d(x,y) | 计算x和y的并集,并返回有序结果 |
in1d(x,y) | 得到一个表述“x的元素是否包含于y”的布尔型数组 |
setdiff1d(x,y) | 集合的差,即元素在x中且不在y中 |
setxor1d(x,y) | 集合的异或,即存在于一个数组中但不同时存在于两个数组中的元素 |
例如
import numpy as np
import numpy.random as np_random
print('用unique函数去重')
names=np.array(['Bob','Joe','Will','Bob','Will','Joe','Joe'])
print(sorted(set(names))) #传统python做法
print(np.unique(names))
ints=np.array([3,3,3,2,2,1,1,4,4])
print(np.unique(ints))
#输出结果
用unique函数去重
['Bob', 'Joe', 'Will']
['Bob' 'Joe' 'Will']
[1 2 3 4]
print('查找数组元素是否在另一个数组')
values=np.array([6,0,0,3,2,5,6])
print(np.in1d(values,[2,3,6]))#中间的是数字1
#输出结果
查找数组元素是否在另一个数组
[ True False False True True False True]
10、用于数组的文件的输入输出
NumPy能够读写磁盘上的文本数据或二进制数据
1、将数组以二进制格式保存到磁盘
np.save和np.load是读写磁盘数组数据的两个主要函数。默认情况下,数组使以未压缩的原始二进制格式保存在扩展名为.npy的文件中的。
arr=np.arange(10)
np.save('E:\some_array',arr)#如果文件路径末尾没有扩展名.npy,则该扩展名会被自动加上
np.load('E:\some_array.npy')
#输出结果
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
通过np.savez可以将多个数组保存到一个压缩文件中,将数组以关键字参数的形式传入即可:
# 数组可以用关键字参数,关键字可以做为加载字典的key,不写的话,key为数组名_索引号
np.savez('some_array_achive.zip',arr,arr)
#加载npz文件时,会得到一个类似字典的对象,该对象会对各个数组进行延迟加载
arch=np.load("some_array_achive.zip.npz")
arch['arr_0']
#输出结果
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
np.savez('some_array_archive.npz',a=arr,b=arr)
arch=np.load('some_array_archive.npz')
arch['b']
#输出结果
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
2、存取文本文件
函数为savetxt和loadtxt,delimiter用于指定分隔符。
arr=np.arange(15).reshape(3,5)
np.savetxt('E:\\number.txt',arr)#默认是以空格存储
np.loadtxt('E:\\number.txt',delimiter=' ')
#输出结果
array([[ 0., 1., 2., 3., 4.],
[ 5., 6., 7., 8., 9.],
[10., 11., 12., 13., 14.]])
arr=np.arange(15).reshape(3,5)
np.savetxt('E:\\number.txt',arr,fmt="%d", delimiter=",")##改为保存为整数,以逗号分隔
np.loadtxt('E:\\number.txt',delimiter=',')#读入时也需要指定逗号分隔
#输出结果
array([[ 0., 1., 2., 3., 4.],
[ 5., 6., 7., 8., 9.],
[10., 11., 12., 13., 14.]])
11、线性代数相关知识
1、常用的numpy.linalg函数
类型 | 说明 |
---|---|
diag | 以一维数组的形式返回方阵的对角线(或非对角线元素),或将一维数组转换为方阵(非对角线元素为0) |
dot | 矩阵乘法 |
trace | 计算对角线元素的和 |
det | 计算矩阵行列式 |
eig | 计算方阵的特征值和特征向量 |
inv | 计算方阵的逆 |
pinv | 计算矩阵的Moore-Penrose伪逆 |
qr | 计算QR分解 |
svd | 计算奇异值分解 |
solve | 解线性方程Ax=b,其中A为一个方阵 |
lstsq | 计算Ax=b的最小二乘法 |
2、随机数生成
部分numpy.random函数
类型 | 说明 |
---|---|
seed | 确定随机数生成器的种子 |
permutation | 返回一个序列的随机排列或返回一个随机排列的返回 |
shuffle | 对一个序列就地随机乱序 |
rand | 产生均匀分布的样本值 |
randint | 从给定的上下限范围内随机选取整数 |
randn | 产生正态分布(平均值为0,标准差为1) |
binomial | 产生二项分布的样本值 |
normal | 产生正态(高斯)分布的样本值 |
beta | 产生Beta分布的样本值 |
chisquare | 产生卡方分布的样本值 |
gamma | 产生Gamma分布的样本值 |
uniform | 产生在[0,1]中均匀分布的样本值 |
举例说明一下:
import numpy as np
import numpy.random as np_random
from numpy.linalg import inv,qr #np.linalg.qr() 计算矩阵的QR分解。把矩阵A作为QR,q是正交的,r是上三角形。
print('矩阵乘法')
x=np.array([[1,2,3],[4,5,6]])
y=np.array([[6,23],[-1,7],[8,9]])
print(x.dot(y))
print(np.dot(x,np.ones(3)))
#输出结果
矩阵乘法
[[ 28 64]
[ 67 181]]
[ 6. 15.]
print('矩阵求逆')
x=np_random.randn(5,5)
mat=x.T.dot(x)
print(mat)
print(inv(mat)) #矩阵求逆
#输出结果
矩阵求逆
[[ 1.98865642 0.87621711 0.50914973 -0.59201157 1.4962339 ]
[ 0.87621711 3.21679405 -2.71081078 -2.47261804 3.30593938]
[ 0.50914973 -2.71081078 3.95085603 1.98369356 -3.06847868]
[-0.59201157 -2.47261804 1.98369356 2.28325811 -1.90019395]
[ 1.4962339 3.30593938 -3.06847868 -1.90019395 5.32927538]]
[[ 2.51522146 0.5094521 -2.05939265 1.64310943 -1.62208792]
[ 0.5094521 8.5351535 0.03408685 6.87711283 -2.96597858]
[-2.05939265 0.03408685 2.30160136 -1.32271445 1.4106317 ]
[ 1.64310943 6.87711283 -1.32271445 6.95687878 -3.00849462]
[-1.62208792 -2.96597858 1.4106317 -3.00849462 2.22246694]]
print('矩阵消元')
print(mat)
q,r=qr(mat)
print(q)
print(r)
#输出结果
矩阵消元
[[ 1.98865642 0.87621711 0.50914973 -0.59201157 1.4962339 ]
[ 0.87621711 3.21679405 -2.71081078 -2.47261804 3.30593938]
[ 0.50914973 -2.71081078 3.95085603 1.98369356 -3.06847868]
[-0.59201157 -2.47261804 1.98369356 2.28325811 -1.90019395]
[ 1.4962339 3.30593938 -3.06847868 -1.90019395 5.32927538]]
[[-0.7227447 0.33998332 0.10879741 0.50419857 -0.30983603]
[-0.3184468 -0.43592479 -0.4689645 -0.4094794 -0.56653343]
[-0.18504216 0.69437513 -0.43057462 -0.47498117 0.26944565]
[ 0.21515694 0.35644137 0.57379943 -0.40888083 -0.57465444]
[-0.54378178 -0.29184524 0.5035823 -0.43048784 0.4245148 ]]
[[-2.75153372 -3.4857553 1.85957706 2.37275326 -4.8731658 ]
[ 0. -4.83286671 5.70077957 3.62243914 -5.29575305]
[ 0. 0. -0.78145947 0.59426082 1.52702576]
[ 0. 0. 0. -0.3437924 -0.65908086]
[ 0. 0. 0. 0. 0.19101063]]
三、NumPy高级应用
1、数组重塑
import numpy as np
print('将一位数组转化为二维数组')
arr=np.arange(8)
print(arr)
print(arr.reshape((4,2)))
print(arr.reshape((4,2)).reshape((2,4))) #支持链式操作
#输出结果
将一位数组转化为二维数组
[0 1 2 3 4 5 6 7]
[[0 1]
[2 3]
[4 5]
[6 7]]
[[0 1 2 3]
[4 5 6 7]]
print('纬度大小自动推导')
arr=np.arange(15)
print(arr.reshape((5,-1)))
#输出结果
纬度大小自动推导
[[ 0 1 2]
[ 3 4 5]
[ 6 7 8]
[ 9 10 11]
[12 13 14]]
print('获取维度信息并应用')
other_arr=np.ones((3,5))
print(other_arr.shape)
print(arr.reshape(other_arr.shape))
#输出结果
获取维度信息并应用
(3, 5)
[[ 0 1 2 3 4]
[ 5 6 7 8 9]
[10 11 12 13 14]]
print('高维数组拉平')
arr=np.arange(15).reshape((5,3))
print(arr.ravel())
#输出结果
高维数组拉平
[ 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14]
2、数组的合并和拆分
数组连接函数
类型 | 说明 |
---|---|
concatenate | 最一般化的连接,沿一条轴连接一组数组 |
vstack,row_stack | 以面向行的方式对数组进行堆叠(沿轴0) |
hstack | 以面向行的方式对数组进行堆叠(沿轴1) |
column_stack | 类似于hstack,但是会先将一维数组转换为二维列向量 |
dstack | 以面向“深度”的方式对数组进行堆叠(沿轴2) |
split | 沿指定轴在指定的位置拆分数组 |
hsplit,vsplit,dsplit | split的便捷化函数,分别沿着轴0、轴1和轴2进行拆分 |
举例说明
import numpy as np
import numpy.random as np_random
print('连接两个二维数组')
arr1=np.array([[1,2,3],[4,5,6]])
arr2=np.array([[7,8,9],[10,11,12]])
print(np.concatenate([arr1,arr2],axis=0)) #按行连接
print(np.concatenate([arr1,arr2],axis=1)) #按列连接
#输出结果
连接两个二维数组
[[ 1 2 3]
[ 4 5 6]
[ 7 8 9]
[10 11 12]]
[[ 1 2 3 7 8 9]
[ 4 5 6 10 11 12]]
#所谓堆叠,可以参考叠盘子...连接的另一种表述
print('垂直stack与水平stack')
print(np.vstack((arr1,arr2))) #垂直堆叠
print(np.hstack((arr1,arr2))) #水平堆叠
#输出结果
垂直stack与水平stack
[[ 1 2 3]
[ 4 5 6]
[ 7 8 9]
[10 11 12]]
[[ 1 2 3 7 8 9]
[ 4 5 6 10 11 12]]
print('拆分数组')
arr=np_random.randn(5,5)
print('水平拆分')
#split() 默认沿着轴 0 分裂,其第二个参数 [1, 3] 相当于是个切片操作,将数组分成三部分:
#第一部分 - :1 (即第 1 行)
#第二部分 - 1:3 (即第 2 到 3 行)
#第二部分 - 3: (即第 4 到 5 行)
first,second,third=np.split(arr,[1,3],axis=0)
print('first')
print(first)
print('second')
print(second)
print('third')
print(third)
#输出结果
拆分数组
水平拆分
first
[[-0.46491171 -0.19058384 -1.07364092 -1.85470984 0.25540176]]
second
[[ 1.74812413 -1.68223681 -0.36129552 -0.55700583 -0.07995627]
[ 0.23844452 -0.4824581 -0.80981716 -2.03862077 0.80593082]]
third
[[-0.46856153 -0.65257412 1.56297046 -0.88790314 0.9681378 ]
[ 0.39970154 -0.02626426 -0.49439246 0.33935688 1.11579582]]
print('垂直拆分')
first,second,third=np.split(arr,[1,3],axis=1)
print('first')
print(first)
print('second')
print(second)
print('third')
print(third)
#输出结果
垂直拆分
first
[[-0.46491171]
[ 1.74812413]
[ 0.23844452]
[-0.46856153]
[ 0.39970154]]
second
[[-0.19058384 -1.07364092]
[-1.68223681 -0.36129552]
[-0.4824581 -0.80981716]
[-0.65257412 1.56297046]
[-0.02626426 -0.49439246]]
third
[[-1.85470984 0.25540176]
[-0.55700583 -0.07995627]
[-2.03862077 0.80593082]
[-0.88790314 0.9681378 ]
[ 0.33935688 1.11579582]]
3、元素的重复操作
import numpy as np
import numpy.random as np_random
print('Repeat:按元素')
arr=np.arange(3)
print(arr.repeat(3))
print(arr.repeat([2,3,4])) #3个元素,分别复制2,3,4次,长度要匹配
#输出结果
Repeat:按元素
[0 0 0 1 1 1 2 2 2]
[0 0 1 1 1 2 2 2 2]
print('Repeat:指定轴')
arr=np_random.randn(2,2)
print(arr)
print(arr.repeat(2,axis=0))#按行repeat
print(arr.repeat(2,axis=1))#按列repeat
#输出结果
Repeat:指定轴
[[1.50330034 0.35285254]
[0.22505996 1.09992342]]
[[1.50330034 0.35285254]
[1.50330034 0.35285254]
[0.22505996 1.09992342]
[0.22505996 1.09992342]]
[[1.50330034 1.50330034 0.35285254 0.35285254]
[0.22505996 0.22505996 1.09992342 1.09992342]]
print('Tile:参考贴瓷砖')
print(np.tile(arr,2))
print(np.tile(arr,(2,3)))#指定每个轴的tile次数
#输出结果
Tile:参考贴瓷砖
[[1.50330034 0.35285254 1.50330034 0.35285254]
[0.22505996 1.09992342 0.22505996 1.09992342]]
[[1.50330034 0.35285254 1.50330034 0.35285254 1.50330034 0.35285254]
[0.22505996 1.09992342 0.22505996 1.09992342 0.22505996 1.09992342]
[1.50330034 0.35285254 1.50330034 0.35285254 1.50330034 0.35285254]
[0.22505996 1.09992342 0.22505996 1.09992342 0.22505996 1.09992342]]
4、花式索引的等价函数
1、take
2、put
import numpy as np
import numpy.random as np_random
print('Fancy Indexing 例子代码')
arr=np.arange(10)*100
print(arr)
inds=[7,1,2,6]
print(arr[inds])
#输出结果
Fancy Indexing 例子代码
[ 0 100 200 300 400 500 600 700 800 900]
[700 100 200 600]
print('使用take')
print(arr.take(inds))
#输出结果
使用take
[700 100 200 600]
print('使用put更新内容')
arr.put(inds,50)
print(arr)
#输出结果
使用put更新内容
[ 0 50 50 300 400 500 50 50 800 900]
arr.put(inds,[70,10,20,60])
print(arr)
#输出结果
[ 0 10 20 300 400 500 60 70 800 900]
Numpy的学习就到这里,以上的代码都是在jupyter上面实现的,希望大家都可以敲一敲,接下来更新的是关于Pandas库的学习。