简介
NumPy(Numerical Python)是Python的一种开元的数值计算扩展。提供对位数组对象,各种派生对象(如掩码数组、矩阵),这种工具可用来存储和处理大型矩阵,比Python资深的嵌套列表(nested list structure)结构要高效很多(该结构也可用来标识矩阵),支持大量的维度数组与矩阵运算,此外也针对数组运算提供大量的数学函数库,包括数学、逻辑、形状操作、排序、选择、输入输出、离散傅立叶变换、基本线性代数、基本统计运算、随机模拟等。
- 几乎所有从事Python工作的数据分析师都使用Numpy的强大功能
- 强大的N维数组
- 成熟的广播功能
- 用于整合C/C++和Fortran代码的工具包
- 提供了全面的数学功能
安装
pip install numpy -i https://pypi.tuna.tsinghua.edu.cn/simple
使用
创建方式
方式一 list转换
import numpy
lst = [1, 2, 3, 4, 5, 6]
arr = numpy.array(lst)
方式二 默认值初始化创建
import numpy
arr2 = numpy.ones(10, detype=int)
arr3 = numpy.zeros(10)
arr4 = numpy.full(shape=5, fill_value=3.)
print(arr2)
print(arr3)
print(arr4)
运行结果
[1 1 1 1 1 1 1 1 1 1]
[0. 0. 0. 0. 0. 0. 0. 0. 0. 0.]
[3. 3. 3. 3. 3.]
ones和zeros、full生成一定数量的数组,里边内容都是一样的,但是ones和zeros的默认值类型是float
方式三 其他方式(随机数、等差、等比等)创建
import numpy
# 随机数
r1 = numpy.random.randint(100)
print('随机数:', r1)
r2 = numpy.random.randint(100, size=(5, 6))
print(r2)
print("形状:", r2.shape)
print("类型:", r2.dtype)
print("维度:", r2.ndim)
print("字节数:", r2.itemsize)
# 正态分布
rn = numpy.random.randn(10)
# 等差数列
lp = numpy.linspace(1, 99, 50)
print('等差数列:', lp)
lp3 = numpy.arange(start=0, stop=20, step=2)
print(lp3)
# 设置不显示科学计数法
numpy.set_printoptions(suppress=True)
# 等比数列 默认是科学计数法显示,需要通过上述方式关闭
lp2 = np.logspace(1, 10, base=2, num=10)
print('等比数列:', lp2)
随机数: 12
[[10 99 23 13 46 39]
[89 62 58 51 32 94]
[38 7 53 86 49 79]
[23 16 3 86 89 74]
[82 94 6 16 95 63]]
形状: (5, 6)
类型: int32
维度: 2
字节数: 4
等差数列: [ 1. 3. 5. 7. 9. 11. 13. 15. 17. 19. 21. 23. 25. 27. 29. 31. 33. 35.
37. 39. 41. 43. 45. 47. 49. 51. 53. 55. 57. 59. 61. 63. 65. 67. 69. 71.
73. 75. 77. 79. 81. 83. 85. 87. 89. 91. 93. 95. 97. 99.]
[ 0 2 4 6 8 10 12 14 16 18]
等比数列: [ 2. 4. 8. 16. 32. 64. 128. 256. 512. 1024.]
存储
import numpy
numpy.set_printoptions(suppress=True)
arr = numpy.arange(0, 10, 3)
# 单个数组存储和读取
numpy.save('./numpy_io.npy', arr)
arr2 = numpy.load('./numpy_io.npy')
print(arr2)
arr3 = numpy.logspace(0, 10, base=2, num=11, dtype=int)
# 压缩存储,生成npz文件,load的时候需要指定key获取,savez的时候如果没指定key,默认是arr_0,arr_1……
numpy.savez('./numpy_io.npz', x=arr, y=arr3)
arr4 = numpy.load('./numpy_io.npz')['y']
print(arr4)
数据类型
# uint8 无符号,没有负号,没有负数 (0, 255)
# int8 有符号,有负号,有负数 (-128, 127)
# int: int8、uint8、int16、int32、int64
# float: float16、float32、float64
# str
转换数据类型 astype
arr5 = numpy.logspace(0, 10, base=2, num=11, dtype=numpy.int32)
arr6 = arr5.astype(numpy.float32)
print(arr6)
数组运算
import numpy
numpy.set_printoptions(suppress=True)
nd = numpy.random.randint(0, 10, size=(3, 5))
print(nd)
print("四则运算:+、-、*、/、//、%、**")
print(nd ** 3)
print("math类中的各种方法:power……")
print(numpy.power(nd, 3))
print("逻辑运算:>、<、>=、<=、==")
print(nd >= 5)
print("赋值操作:+=、-=、*=、**=、//=、%=,唯独不支持/=操作")
nd //= 2
print(nd)
[[8 4 1 0 1]
[1 1 5 4 0]
[0 4 8 3 6]]
四则运算:+、-、*、/、//、%、**
[[512 64 1 0 1]
[ 1 1 125 64 0]
[ 0 64 512 27 216]]
math类中的各种方法:power……
[[512 64 1 0 1]
[ 1 1 125 64 0]
[ 0 64 512 27 216]]
逻辑运算:>、<、>=、<=、==
[[ True False False False False]
[False False True False False]
[False False True False True]]
赋值操作:+=、-=、*=、**=、//=、%=,唯独不支持/=操作
[[4 2 0 0 0]
[0 0 2 2 0]
[0 2 4 1 3]]
拷贝
无拷贝
import numpy
a = numpy.random.randint(0, 100, size=(2, 5))
b = a
# Ture,b指向a的对象,没有拷贝任何内容
print(a is b)
b[0][0] = 1024
print(a)
print(b)
True
[[1024 66 26 59 76]
[ 44 60 21 46 92]]
[[1024 66 26 59 76]
[ 44 60 21 46 92]]
浅拷贝
import numpy
# 浅拷贝
a = numpy.random.randint(0, 100, size=(2, 5))
b = a.view()
print(a is b)
print(b.base is a)
print(b.flags.owndata)
print(a.flags.owndata)
b[0][0] = 1024
print(a)
print(b)
False
True
False
True
[[1024 8 63 28 83]
[ 20 43 85 58 51]]
[[1024 8 63 28 83]
[ 20 43 85 58 51]]
深拷贝
import numpy
# 深拷贝
a = numpy.random.randint(0, 100, size=(2, 5))
b = a.copy()
print(a is b)
print(b.base is a)
print(b.flags.owndata)
print(a.flags.owndata)
b[0][0] = 1024
print(a)
print(b)
False
False
True
True
[[16 28 0 88 43]
[37 40 35 40 94]]
[[1024 28 0 88 43]
[ 37 40 35 40 94]]
行列交换
import numpy
# 列变换
arr2 = numpy.random.randint(0, 100, size=(5, 6))
print(arr2)
index = numpy.argsort(arr2[:, 2])
print(index)
print(arr2[:, index])
[[48 81 25 46 1 50]
[39 57 45 16 18 84]
[19 29 0 50 94 24]
[58 42 7 52 27 79]
[83 23 5 53 39 14]]
[2 4 3 0 1]
[[25 1 46 48 81]
[45 18 16 39 57]
[ 0 94 50 19 29]
[ 7 27 52 58 42]
[ 5 39 53 83 23]]
切片
取任意行和列的数据组成新的数组
import numpy
arr = numpy.random.randint(0, 100, size=(5, 6))
print(arr)
print(arr[[1, 3]][:, [0, 1, 4]])
print(arr[numpy.ix_([1, 3], [0, 1, 4])])
[[38 19 2 34 22 61]
[90 26 35 56 82 17]
[21 47 86 15 80 40]
[ 6 80 63 12 45 82]
[58 73 97 10 4 18]]
[[90 26 82]
[ 6 80 45]]
[[90 26 82]
[ 6 80 45]]
数组变形
reshape 变形
变形需要数组总数一致,否则异常。如果不想计算可以使用-1,会自动按照另一个值计算后得出
import numpy
arr3 = numpy.random.randint(0, 100, size=(5, 6))
print(arr3)
print(arr3.reshape(2, 15))
print(arr3.reshape(-1, 15))
[[ 9 87 11 14 25 10]
[65 19 75 95 5 45]
[67 49 42 62 25 41]
[66 0 25 29 57 83]
[14 65 27 29 8 10]]
[[ 9 87 11 14 25 10 65 19 75 95 5 45 67 49 42]
[62 25 41 66 0 25 29 57 83 14 65 27 29 8 10]]
[[ 9 87 11 14 25 10 65 19 75 95 5 45 67 49 42]
[62 25 41 66 0 25 29 57 83 14 65 27 29 8 10]]
concatenate 叠加
把多个数组合并到一起,,0-默认值,代表行(增加),表示按列合并;1-代表列(增加),表示按行合并
- 1-按行合并(一行一行的合并)时,行的数量必须一致,左右叠加
- 0-按列合并(一列一列的合并)时,列的数量必须一致,上下叠加
arr4 = numpy.random.randint(0, 100, size=(3, 4))
arr5 = numpy.random.randint(0, 100, size=(3, 5))
print(arr4)
print(arr5)
# 参数axis表示是否可以合并,0-默认值,按列合并;1-按行合并
arr6 = numpy.concatenate([arr4, arr5], axis=1)
print(arr6)
[[65 74 2 44]
[15 32 17 50]
[76 46 95 53]]
[[29 83 99 46 8]
[23 2 18 2 4]
[47 13 70 95 48]]
[[65 74 2 44 29 83 99 46 8]
[15 32 17 50 23 2 18 2 4]
[76 46 95 53 47 13 70 95 48]]
split 拆分
import numpy
arr7 = numpy.random.randint(0, 100, size=(6, 10))
print(arr7)
# 3表示平均拆成3分,不能整除就会异常
print(numpy.split(arr7, 3))
# [1, 3, 4] 表示从索引1,3,4前分别切割,默认行索引号
print(numpy.split(arr7, [1, 3, 4]))
# axis=1表示列索引号,从第1、3、4列前切割
print(numpy.split(arr7, [1, 3, 4], axis=1))
[[84 15 40 65 90 41 88 5 88 87]
[51 98 64 71 31 9 89 49 51 65]
[25 54 33 84 5 88 65 64 22 72]
[91 32 33 52 15 25 11 23 36 31]
[12 71 85 0 63 3 43 83 6 98]
[76 23 88 45 24 93 17 84 59 97]]
[array([[84, 15, 40, 65, 90, 41, 88, 5, 88, 87],
[51, 98, 64, 71, 31, 9, 89, 49, 51, 65]]), array([[25, 54, 33, 84, 5, 88, 65, 64, 22, 72],
[91, 32, 33, 52, 15, 25, 11, 23, 36, 31]]), array([[12, 71, 85, 0, 63, 3, 43, 83, 6, 98],
[76, 23, 88, 45, 24, 93, 17, 84, 59, 97]])]
[array([[84, 15, 40, 65, 90, 41, 88, 5, 88, 87]]), array([[51, 98, 64, 71, 31, 9, 89, 49, 51, 65],
[25, 54, 33, 84, 5, 88, 65, 64, 22, 72]]), array([[91, 32, 33, 52, 15, 25, 11, 23, 36, 31]]), array([[12, 71, 85, 0, 63, 3, 43, 83, 6, 98],
[76, 23, 88, 45, 24, 93, 17, 84, 59, 97]])]
[array([[84],
[51],
[25],
[91],
[12],
[76]]), array([[15, 40],
[98, 64],
[54, 33],
[32, 33],
[71, 85],
[23, 88]]), array([[65],
[71],
[84],
[52],
[ 0],
[45]]), array([[90, 41, 88, 5, 88, 87],
[31, 9, 89, 49, 51, 65],
[ 5, 88, 65, 64, 22, 72],
[15, 25, 11, 23, 36, 31],
[63, 3, 43, 83, 6, 98],
[24, 93, 17, 84, 59, 97]])]
transpose 数组转置
import numpy
arr8 = numpy.random.randint(0, 100, size=(4, 2))
print(arr8)
# 行变列,列变行
print(numpy.transpose(arr8))
print('------------------------------------------------------------------------------')
[[ 0 85]
[69 20]
[99 29]
[97 81]]
[[ 0 69 99 97]
[85 20 29 81]]
广播机制
import numpy
arr1 = numpy.random.randint(0, 10, size=(5, 3))
arr2 = numpy.arange(1, 4)
print(arr1)
print(arr2)
print(arr1 + arr2)
[[0 8 8]
[8 2 3]
[5 4 7]
[8 8 9]
[5 9 5]]
[1 2 3]
[[ 1 10 11]
[ 9 4 6]
[ 6 6 10]
[ 9 10 12]
[ 6 11 8]]
通用函数
一般数学函数
import numpy
numpy.set_printoptions(suppress=True)
# π
print(numpy.pi)
# sin、cos
print(numpy.sin(numpy.pi / 2))
print(numpy.sin(0))
print(numpy.cos(0))
print(numpy.cos(numpy.pi / 2).round(4))
# 开平方
print(numpy.sqrt(1024))
# 平方
print(numpy.square(4))
# n次方
print(numpy.power(27, 1/3))
# 对数
print(numpy.log2(16))
# 返回两个数组比较大、小的值
x = numpy.array([1, 5, 2, 9, 3, 6, 8])
y = numpy.array([2, 4, 3, 7, 1, 9, 0])
print('返回两个数组中大的值:', numpy.maximum(x, y))
print('返回两个数组中大的值:', numpy.minimum(x, y))
# 返回两个数组的内积
arr1 = numpy.random.randint(0, 10, size=(2, 2))
print(arr1)
print("内积为:\n", numpy.inner(arr1, arr1))
# 取整
print(numpy.ceil(3.01))
print(numpy.round(3.01, 1))
print(numpy.round(3.99, 1))
print(numpy.floor(3.99))
# clip裁剪,小于10,拔高为10,大于30,降低为30
arr2 = numpy.random.randint(0, 50, size=20)
print(arr2)
print(numpy.clip(arr2, 10, 30))
3.141592653589793
1.0
0.0
1.0
0.0
32.0
16
3.0
4.0
返回两个数组中大的值: [2 5 3 9 3 9 8]
返回两个数组中大的值: [1 4 2 7 1 6 0]
[[5 6]
[7 6]]
内积为:
[[61 71]
[71 85]]
4.0
3.0
4.0
3.0
[ 2 28 47 27 21 23 17 1 17 16 31 3 27 7 43 43 11 21 42 10]
[10 28 30 27 21 23 17 10 17 16 30 10 27 10 30 30 11 21 30 10]
where函数
import numpy
x = numpy.array([1, 5, 2, 9, 3, 6, 8])
y = numpy.array([2, 4, 3, 7, 1, 9, 0])
cond = numpy.array([True, False, True, True, False, False, True])
# where 根据条件选择取值,值为True,从第一个数组中取值,False则从第二个数组取值
print(numpy.where(cond, x, y))
# where 根据条件选择取值,值为True,从第一个数组中取值,False则取0
print(numpy.where(x < 5, x, 0))
[1 4 2 9 1 9 8]
[1 0 2 0 3 0 0]
集合运算函数
import numpy
x = numpy.array([1, 5, 2, 9, 3, 6, 8])
y = numpy.array([2, 4, 3, 7, 1, 9, 0])
# 交集
print(numpy.intersect1d(x, y))
# 并集
print(numpy.union1d(x, y))
# 差集
print(numpy.setdiff1d(x, y))
[1 2 3 9]
[0 1 2 3 4 5 6 7 8 9]
[5 6 8]
统计函数
min、max、mean、median、sum、std、var、cunsum、cumprod、argmin、argmax、argwhere、cov、corrcoef
矩阵运算
import numpy
from numpy.linalg import det, inv
numpy.set_printoptions(suppress=True)
nd = numpy.random.randint(0, 10, size=(3, 5))
print(nd)
ne = numpy.random.randint(0, 10, size=(5, 3))
print(ne)
# 矩阵乘积
print(numpy.dot(nd, ne))
print(nd.dot(ne))
# 方阵
nf = numpy.random.randint(0, 10, size=(3, 3))
# 逆矩阵
print(inv(nf))
# 矩阵行列式
print(det(nf))
[[2 4 3 0 2]
[3 0 1 4 4]
[2 2 3 0 3]]
[[1 8 6]
[8 0 2]
[0 6 2]
[9 2 6]
[6 1 8]]
[[46 36 42]
[63 42 76]
[36 37 46]]
[[46 36 42]
[63 42 76]
[36 37 46]]
[[ 0.25732899 -0.01302932 -0.14006515]
[-0.18566775 -0.00325733 0.21498371]
[-0.13029316 0.12052117 0.04560261]]
-306.9999999999999