(numpy)Python做数据处理必备框架!(二):ndarray切片的使用与运算;常见的ndarray函数:平方根、正余弦、自然对数、指数、幂等运算;统计函数:方差、均值、极差;比较函数...
ndarray切片
索引从0开始
import numpy as nparr = np.random.randint(1,100,20)print(arr)# [31 78 14 48 91 1 79 47 75 45 80 90 65 2 77 51 81 60 84 50]# 索引和切片的用法与python基本语法完全一致print(arr[10])print(arr[:]) print(arr[2:5])
特殊用法-布尔索引
print(arr[arr>20])# [31 78 48 91 79 47 75 45 80 90 65 77 51 81 60 84 50]print(arr[(arr>20) & (arr<50)])
slice函数
arr[slice(2,5)]# 等同于arr[2:5]
slice函数还可以定义步长
arr[slice(2,5,2)] # 获取从索引2开始到索引5结束并每个数间隔2个索引值
二维数组
# 二维数组arr = np.random.randint(1,100,(4,4))print(arr)
大体写法一致
- 二维数组通过
,
号来分别 行列的索引[row,col]
print(arr[1,3]) # 获得在索引1的行上并且索引3的列上的值print(arr[1][3]) # 相同写法print(arr[1,2:5]) # 获取索引1行上满足索引2:5列的值print(arr[2][arr[2]>50]) # 在索引2行上所有满足索引2行中值大于50的值# 若满足条件的值索引不在原行中,那么满足条件的值索引会传导错误的索引print(arr[2][arr[3]>50])
二维数组使用布尔索引后,满足条件返回的数组会是一个一维数组
若要直接获得列的值,好办
print(arr[:,3]) # 获得所有索引3的列值
ndarray的运算
算数运算
在原生Python中,数组之间不能直接进行算数运算
+
运算符只能是拼接作用,而不是加法运算
– 原生Python
c = [1,2,3]d = [4,5,6]print(c+d) # [1 2 3 4 5 6]print(c-d) # 报错# 数组相加for i in range(len(c)): c[i] += d[i]print(c) # [5,7,9]
在numpy中,可以直接运算
a = np.array([1,2,3])b = np.array([4,5,6])print(a+b) # [5 7 9]print(a-b) # [-3 -3 -3]print(a*b) # [ 4 10 18]print(a/b) # [0.25 0.4 0.5 ]print(a%b) # [1 2 3]print(a**b) # [ 1 32 729]
- 行列之间与索引挂钩,两个数组之间按照相同索引进行算数运算
# 算数运算a = np.array([[1,2,3],[4,5,6],[7,8,9]])b = np.array([[7,8,9],[4,5,6],[1,2,3]])print(a+b)print(a-b)print(a*b)print(a/b)print(a%b)print(a**b)#[[ 8 10 12]# [ 8 10 12]# [ 8 10 12]]#[[-6 -6 -6]# [ 0 0 0]# [ 6 6 6]]#[[ 7 16 27]# [16 25 36]# [ 7 16 27]]#[[0.14285714 0.25 0.33333333]# [1. 1. 1. ]# [7. 4. 3. ]]#[[1 2 3]# [0 0 0]# [0 0 0]]#[[ 1 256 19683]# [ 256 3125 46656]# [ 7 64 729]]
- 当数组要直接跟数字进行算数运算,是在每个元素上都进行一次运算
a = np.array([[1,2,3],[4,5,6],[7,8,9]])print(a + 10)# [[11 12 13]# [14 15 16]# [17 18 19]]
广播机制
当数组之间维度不同,可以使用广播机制进行交叉运算
条件(或):
- 行或列需要一致
- 行为1列不为1 或者 行不为1列为1
- 行列之间维度必须一致
# 广播机制a = np.array([1,2,3]) # 1*3b = np.array([[1],[2],[3]])# 3*1print(a+b)#[[2 3 4]# [3 4 5]# [4 5 6]]
矩阵运算
a = np.array([[1,2,3],[4,5,6],[7,8,9]])b = np.array([[7,8,9],[4,5,6],[1,2,3]])print(a @ b) # 求a和b的矩阵值
\'\'\'a:[[1 2 3] [4 5 6] [7 8 9]] b:[[7 8 9] [4 5 6] [1 2 3]] \'\'\'
如何求矩阵?numpy中求矩阵值的符号为:@
其原理是获得a数组的行和b数组的列然后进行相加。
例如求索引(1,2)的矩阵值:
-
获得 a数组在 第1行 上的所有值;相当于
a[1,]
[1 2 3]
-
获得 b数组在 第2列 上的所有值;相当于
b[,2]
[8 5 2]
-
将上述两个数组筛选出来的值,按照对应索引相乘后再相加,得到矩阵在(1,2)索引位置的值
(1*8)+(2*5)+(3*2)= 24
# 矩阵运算a = np.array([[1,2,3],[4,5,6],[7,8,9]])b = np.array([[7,8,9],[4,5,6],[1,2,3]])print(a)print(b)print(a[1,])print(b[:,2])print(\'##########\')print(a @ b)# 举证值\'\'\'[[ 18 24 30] [ 54 69 84] [ 90 114 138]]\'\'\'
在获得行列步骤中,锁定行列的不是索引,直接是第几行或第几列
常用函数
-
基本数学
- np.sqrt(x)
- np.exp(x)
- np.log(x)
- np.sin(x)
- np.abs(x)
- np.power(a,b)
- np.round(x,n)
-
统计
- np.sum(x)
- np.mean(x)
- np.std(x)
- np.var(x)
- np.min(x)
- np.max(x)
- np.percentile(x,q)
-
比较
np.greater(a,b)
np.less(a,b)
np.equal(a,b)
np.logical_and(a,b)
np.where(conditaion,x,y)
-
去重
- np.unique(x)
- np.in1d(a,b)
-
其他
- np.concatenate((a,b))
- np.split(x,indices)
- np.reshape(x,shape)
- np.copy(x)
- np.isnan(x)
-
排序
-
np.sort(x)
-
x.sort()
-
np.argsort(x)
-
np.lexsort(keys)
-
计算平方根
print(np.sqrt(9))print(np.sqrt([1,2,4]))arr = np.array([16,50,81])print(np.sqrt(arr))\'\'\'3.0[1. 1.41421356 2. ][4. 7.07106781 9. ]\'\'\'
计算指数
-
e x = y e^x=y ex=y
-
默认以
e(2.71)
为底
print(np.exp(0))print(np.exp(1))print(np.exp(5))\'\'\'1.02.718281828459045148.4131591025766\'\'\'
计算自然对数
- l n y = x lny =x lny=x
print(np.log(2.71)) # 0.99....
计算正弦、余弦…
# 将角度转换为弧度def catchNum(x): return x*np.pi/180 print(np.sin(catchNum(135)))print(np.cos(np.pi))print(np.tan(catchNum(90)))\'\'\'0.7071067811865476-1.01.633123935319537e+16\'\'\'
- numpy中计算正余弦这类函数,传入的是一个弧度,而不是角度,所以还需要将角度转换为弧度
绝对值
# 绝对值arr = np.array([-1,1,2,3,-3])print(np.abs(arr)) # [1 1 2 3 3]
幂运算
print(np.power(arr,3)) # [ -1 1 8 27 -27]
四舍五入-向下或向下取整
print(np.round([3.2,4.5,5,8.1,9.67])) # [ 3. 4. 5. 8. 10.]
numpy中,x.5会被舍去。这是python自身的问题
- 解决办法就是在小数后添一位数字即可
print(np.round([3.2,4.51,8.1,9.67])) # [ 3. 5. 8. 10.]
向上、向下取整
# 向上向下取整arr = np.array([1.6, 25.1, 3.5])# 向上取整 ceil()print(np.ceil(arr)) # [ 2. 26. 4.]# 向下取整 floor()print(np.floor(arr)) # [ 1. 25. 3.]
检测缺失值NaN
np.isnan([1,2,np.nan,3])# array([False, False, True, False])
统计函数
基本统计 均值、方差、标准差、求和最大最小值
- 默认执行一维运算
arr = np.array([[1, 2, 3], [4, 5, 6]])print(np.mean(arr)) # 均值:3.5print(np.var(arr)) # 方差:2.9166666666666665print(np.std(arr)) # 标准差:1.707825127659933print(np.sum(arr)) # 总和:21print(np.min(arr)) # 最小值:1print(np.max(arr)) # 最大值:6
- 通过指定
axis
属性来决定按 行 还是 列 进行计算axis = 0
按列axis = 1
按行
print(np.mean(arr, axis=0)) # 按列求均值:[2.5 3.5 4.5]print(np.mean(arr, axis=1)) # 按行求均值:[2. 5.]print(np.sum(arr, axis=1)) # 按行求和:[ 6 15]
方差和标准差比均值更能够看出一组数据中的可用率
位置计算 中位数和百分数
- 中位数
.median()
当数组个数为偶数是取中间两个数的平均值
data = np.array([1, 3, 2, 4, 5])print(np.median(data)) # 输出:3.0(排序后中间的数)# 偶数个元素时取中间两个数的平均值data = np.array([1, 2, 3, 4])print(np.median(data)) # 输出:2.5((2+3)/2)
在执行运算前,会将数组排序
通过.percentile()
,可以通过百分数获取数组中的值
data = np.array([1, 2, 3, 4, 5])print(np.percentile(data, 25)) # 第25百分位数:2.0print(np.percentile(data, 50)) # 第50百分位数(中位数):3.0print(np.percentile(data, 75)) # 第75百分位数:4.0print(np.percentile(data, 45)) # 2.8
.percentile()
还可以获取多个位置上的值
a,b = np.percentile(data,[25,75]) # [2. 4.]print(a,b) # 2.0 4.0
求占比:
np.random.seed(0)arr = np.random.randint(1,100,50)print(np.sort(arr))# 获得arr中超过占比90的值num = np.percentile(arr,90)print(np.sort(arr[arr>num]))\'\'\'[10 10 10 13 15 20 20 21 22 24 26 30 32 33 33 36 37 38 40 40 45 47 48 48 50 58 59 65 65 66 66 68 68 70 71 73 75 76 78 80 81 82 83 84 88 88 89 89 89 89] ## 值:[89 89 89 89]\'\'\'
极差 .ptp()
data = np.array([1, 3, 2, 4, 5])print(np.ptp(data)) # 输出:4(5-1)
累计和、累积积
arr = np.array([1,2,3])print(np.sum(arr)) # 求和print(np.cumsum(arr)) # 累积和print(np.cumprod(arr)) # 累积积\'\'\'6[1 3 6][1 2 6]\'\'\'
- 累积和:[1,1+2,1+2+3]
- 累积积:[1,1*2,1*2*3]
比较函数
比较是否大于、小于、等于、等于;逻辑 与、或、非 检查数组中是否有一个True,是否所有的都为True,自定义条件
是否大于、小于
- .greater(arr[],num)
- .less(arr[],num)
arr = np.array(range(1,10))# 是否大于print(np.greater(arr,4))# 是否小于print(np.less(arr,4))\'\'\'[False False False False True True True True True][ True True True False False False False False False]\'\'\'
- 在一个数组中,判断该数组中所有的元素是否大于或小于指定的num值
二维数组一样比较
arr = np.array([range(1,10),range(11,20)])# 是否大于print(np.greater(arr,4))# 是否小于print(np.less(arr,4))\'\'\'[[False False False False True True True True True] [ True True True True True True True True True]][[ True True True False False False False False False] [False False False False False False False False False]]\'\'\'
是否等于
- .equal(arr[],num)
与大于或小于是一样的
print(np.equal(arr,11))\'\'\'[[False False False False False False False False False] [ True False False False False False False False False]]\'\'\'
矩阵间进行判断
- 矩阵间进行判断需要维度和形状保持一致
arr = [1,2,9]arr1 = [2,3,4]print(np.less(arr,arr1))print(np.greater(arr,arr1))print(np.equal(arr,arr1))\'\'\'[ True True False][False False True][False False False]\'\'\'
- 根据两个数组中对应的索引进行判断
逻辑与或非
arr = [1,0]arr1 = [0,1]arr2 = [1,1]arr3 = [0,0]print(np.logical_and(arr,arr1))print(np.logical_or(arr3,arr1))print(np.logical_not(arr3))\'\'\'[False False][False True][ True True]\'\'\'
检查元素
- any() 检查数组中是否至少有一个为True
- all() 检查数组中的全部元素都为True
print(np.any([0,0,0,0])) # Falseprint(np.all([1,1,1,1])) # True
where()自定义检索
- .where(判断条件,符合条件,不符合条件)
跟三元运算符一个意思
np.random.seed(1)score = np.random.randint(0,101,30)score = np.sort(score)print(score)print(\'#########\')arr = np.where( score<60, # 判断条件 \'不及格\', # 符合条件执行 np.where( # 不符合条件,这里再次进行where筛选 score<80, \'良好\', np.where( score<95, \'优秀\', \'极佳\' ) ))print(arr)\'\'\'[ 1 5 6 9 11 12 13 14 16 18 20 25 28 29 37 50 50 64 68 71 72 75 76 79 84 86 87 87 94 96]#########[\'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'良好\' \'良好\' \'良好\' \'良好\' \'良好\' \'良好\' \'良好\' \'优秀\' \'优秀\' \'优秀\' \'优秀\' \'优秀\' \'极佳\']\'\'\'
select() 条件检索
与where()类似
- np.select(判断条件[],执行结果[],?default)
arr = np.select( [score<60,score<80,score<95,score>=95], # 判断条件 [\'不及格\',\'良好\',\'优秀\',\'极佳\'], # 执行结果 default=\'Null\' # 默认值)print(arr)\'\'\'[\'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'不及格\' \'良好\' \'良好\' \'良好\' \'良好\' \'良好\' \'良好\' \'良好\' \'优秀\' \'优秀\' \'优秀\' \'优秀\' \'优秀\' \'极佳\']\'\'\'
排序与去重函数
排序
-
.sort(数组)
返回排序后的数组
-
.argsort(数组)
获得排序后的值在原数组中的索引
arr = [9,8,5,1,3,4]print(np.sort(arr)) # [1 3 4 5 8 9]print(np.argsort(arr)) # [3 4 5 2 1 0]
去重
-
.unique(arr[])
去除数组中重复的值
arr = np.random.randint(1,100,30)print(np.sort(arr))print(np.sort(np.unique(arr)))\'\'\'[ 1 2 4 4 8 9 10 14 22 23 25 27 31 44 48 50 53 58 58 61 62 64 69 71 72 73 77 81 82 89] [ 1 2 4 8 9 10 14 22 23 25 27 31 44 48 50 53 58 61 62 64 69 71 72 73 77 81 82 89]\'\'\'
- 示例中,58 和 4去重了
拼接、分隔与形状调整
拼接
.concatenate((arr1[],arr2[]),axis)
将两个数组拼接成一个数组
- axis=0:按照row行进行拼接
- axis=1:按照col列进行拼接
arr = np.array([1,2,3])arr1 = np.array([6,4,5])print(np.concatenate((arr,arr1),axis=0)) # [1 2 3 6 4 5]arr = np.array([[1,2,3],[4,5,6]])arr1 = np.array([[7,8,9],[10,11,12]])print(np.concatenate((arr,arr1),axis=1))\'\'\'[[ 1 2 3 7 8 9] [ 4 5 6 10 11 12]]\'\'\'
分隔和形状重调
- 这两个方法的使用前提,都必须要求调整后的数组应符合调整后对应的条件
例如:数组个数为99个,但是要求分割成4个数组,这是不允许的,因为不能够等分的分割
分隔
.split(arr[],num|arr[])
.split(分隔数组,分隔条件)
分隔条件若为数组,则按照索引进行分割
arr = np.array(range(1,101))print(arr)print(np.split(arr,4)) # 分成4份数组\'\'\'[array([ 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]), array([26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50]), array([51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75]), array([ 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100])]\'\'\'
传入数组,则按照索引分割
# 与split(arr,4) 等效print(np.split(arr,[25,50,75]))\'\'\'[array([ 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]), array([26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50]), array([51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75]), array([ 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100])]\'\'\' print(np.split(arr,[25,75]))\'\'\'[array([ 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]), array([26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75]), array([ 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100])]\'\'\'
形状重调
-
reshape(数组,[行,列])
重新调整显示的行列,并返回一个多维数组
print(np.reshape(arr,[5,20]))\'\'\'[# 1[ 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20] # 2[ 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40] # 3[ 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60]# 4[ 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80]# 5[ 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100] ]\'\'\'
🎶😘数据分析章节回顾
(numpy)Python做数据处理必备框架!(一):认识numpy;从概念层面开始学习ndarray数组:形状、数组转置、数值范围、矩阵…
💕👉博客专栏
- 新时代语言Python专栏:基础、Anaconda、数据分析三框架(numpy、pandas、matpltlib)
- Golang专栏-包含基础、Gin、Goam等知识
- 云原生专栏-包含k8s、docker等知识
- 从0开始学习云计算-华为HCIP证书
- JUC专栏-带你快速领悟JUC的知识!
- JVM专栏-深入Java虚拟机,理解JVM的原理
- 基于Java研究 数据结构与算法-包含贪心算法、加权图、最短路径算法等知识
- Docker专栏-上手热门容器技术Docker
- SpringBoot专栏-学习SpringBoot快速开发后端
- 项目管理工具的学习-设计技术:Maven、Git、Gradle等相关管理工具
- JavaSE-全面了解Java基础
- JS专栏-使用JS作的一部分实例~
- 使用CSS所作的一部分案例