1. 数组
-
ndarray是一系列同类型数据的集合,以 0 下标为开始进行集合中元素的索引。
-
ndarray 对象是用于存放同类型元素的多维数组。ndarray 中的每个元素在内存中都有相同存储大小的区域。
1.1 创建数组
最简单的方式是使用array函数来创建数组
data1=[6,7.5,8,0,1]
arr1=np.array(data1)
arr1 # array([6. , 7.5, 8. , 0. , 1. ])
此外,还可以通过以下方法来创建数组
-
从已有数组创建:numpy.asarray(a, dtype = None, order = None)
-
数值接近于0的数组:numpy.empty(shape, dtype = float, order = 'C')
-
全0数组:numpy.zeros(shape, dtype = float, order = 'C')
-
全1数组:numpy.ones(shape, dtype = None, order = 'C')
-
数值范围数组:numpy.arange(start, stop, step, dtype)
-
等差数列:numpy.linspace(start,stop,num,dtype)
-
对角数组:numpy.eye(N, M=None, k=0, dtype=, order='C')
其中shape表示数组形状,dtype为数据类型,order中的C和F分别代表行优先和列优先
具体的创建用例如下:
print("np.zeros((2,2)):\n", np.zeros((2,2)))
print("np.ones((2,2)):\n", np.ones((2,2)))
print("np.eye((2)):\n", np.eye((2)))
print("np.random.random((2,2)):\n", np.random.random((2,2)))
print("np.linspace(1,10,10):\n",np.linspace(1,10,10))
输出结果
np.zeros((2,2)):
[[0.0.]
[0.0.]]
np.ones((2,2)):
[[1.1.]
[1.1.]]
np.eye((2)):
[[1.0.]
[0.1.]]
np.random.random((2,2)):
[[0.572234090.08745789]
[0.540976320.87183112]]
np.linspace(1,10,10):
[ 1.2.3.4.5.6.7.8.9.10.]
1.2 数组对象常用方法
ndarray对象常用方法有以下几种
方法 | 描述 |
---|---|
ndim | 秩,即轴的数量或维度的数量 |
shape | 数组的维度,对于矩阵,n 行 m 列 |
size | 数组元素的总个数 |
dtype | ndarray 对象的元素类型 |
tolist | narray对象转化为list |
newaxis | 给原数组增加一个维度 |
使用这些方法,可以快速的获取数组的一些信息
x=np.array([1,2,3,4,5])
# 秩
print ("x ndim: ", x.ndim)
# 维度
print ("x shape:", x.shape)
# 数组元素的总个数
print ("x size: ", x.size)
# ndarray 对象的元素类型
print ("x dtype: ", x.dtype)
# narray对象转化为list
print("x tolist:",x.tolist())
# 增加维度
print("x newaxis:",x[np.newaxis, :])
输出结果
x ndim: 1
x shape: (5,)
x size: 5
x dtype: int32
x tolist:[1, 2, 3, 4, 5]
x newaxis:[[12345]]
1.3 随机数生成
numpy.random模块对Python内置的random进行了补充,增加了一些用于高效生成多种概率分布的样本值的函数。
函数 | 描述 |
---|---|
random.seed | 随机数生成种子 |
random.permutation | 返回一个序列的随机排列或返回一个随机排列的范围 |
random.shuffle | 对一个序列就地随机排列 |
random.rand | 产生均匀分布的样本值 |
random.randint | 从给定的上下限范围内随机选取整数 |
random.randn | 产生均值为0,标准差为1的正态分布样本值 |
random.binomial | 产生二项分布的样本值 |
random.normal | 产生正态分布样本值 |
random.beta | 产生beta分布的样本值 |
random.chisqure | 产生卡方分布的样本值 |
random.gamma | 产生gamma分布的样本值 |
random.uniform | 产生[0,1)均匀分布的样本值 |
代码演示:
b = np.array([1,2,6,5,8])
# 对b进行随机排列,并返回一个新的数组
print(np.random.permutation(b))
print(b)
# 对b进行随机排列,但不返回一个新的数组,而是直接对b进行修改
np.random.shuffle(b)
print(b)
# 产生均匀分布的样本值,样本值范围在[0,1)间
print(np.random.rand(3,2))
# 在随机生成范围在[1,5)的样本值,且size为3行2列
print(np.random.randint(1,5,size=(3,2)))
# 随机生成2行3列服从标准正态分布的样本值
print(np.random.randn(2,3))
# 随机生成3行2列服从均值为2,标准差为0.2的正态分布样本值
print(np.random.normal(loc=2,scale=0.2,size=(3,2)))
输出结果
# np.random.permutation(b)
[82156]
# b
[12658]
# b
[16258]
# np.random.rand(3,2)
[[0.829364630.09531394]
[0.124837370.72357494]
[0.207779130.36245928]]
# np.random.randint(1,5,size=(3,2))
[[23]
[43]
[43]]
# np.random.randn(2,3)
[[ 0.37613780.10722911-1.26001352]
[ 0.32837867-0.630295350.46372036]]
# np.random.normal(loc=2,scale=0.2,size=(3,2))
[[2.0734912.1170062 ]
[2.059002432.15312689]
[2.156182361.85207286]]
2.数组运算
下面将给大家介绍数组的各种运算方法
2.1 算术运算符
算术运算符是数组中最常用的运算方法,具体算术运算符说明如下
运算符 | 描述 |
---|---|
+ | 加法 |
- | 减法 |
* | 乘法 |
/ | 除法 |
// | 取整除法 |
** | 指数幂 |
% | 模数/余数 |
具体使用方法如下
x = np.arange(4)
print("x =", x)
print("x + 5 =", x + 5)
print("x - 5 =", x - 5)
print("x * 2 =", x * 2)
print("x / 2 =", x / 2)
print("x // 2 =", x // 2)
print("x ** 2 = ", x ** 2)
print("x % 2 = ", x % 2)
输出结果
x = [0123]
x + 5 = [5678]
x - 5 = [-5-4-3-2]
x * 2 = [0246]
x / 2 = [0.0.51.1.5]
x // 2 = [0011]
x ** 2 = [0149]
x % 2 = [0101]
当然,这些运算符也可以用于两个数组的运算,且运算符只作用于位置相同的元素之间
a = np.arange(4)
b = np.arange(4,8)
print(a+b) # [ 4 6 8 10]
print(a-b) # [-4 -4 -4 -4]
print(a*b) # [ 0 5 12 21]
print(a/b) # [0. 0.2 0.33333333 0.42857143]
2.2 广播机制
广播是 numpy 很重要的一个特性,它是对不同形状的数组进行数值计算的方式,通常在数组的算术运算对相应的元素进行。下面举一个最简单的广播案例
x = np.array([1,2,3])
x + 5# array([6, 7, 8])
这里的5在计算前,它先扩展成[5,5,5],然后再与x的对应元素进行相加 更复杂一些的例子,则会涉及到两个数组的广播
a = np.array([1,2,3])
b = np.array([[1,2,3],[4,5,6],[7,8,9]])
a+b
# 输出结果
array([[ 2, 4, 6],
[ 5, 7, 9],
[ 8, 10, 12]])
其广播过程可以用下图来描述
a = np.array([[1],[2],[3]])
b = np.array([[1,2,3],[4,5,6],[7,8,9]])
a + b
其广播过程可以用下图来描述
2.3 自增和自减运算符
当对变量的值进行自增与自减,需要使用+=或-=运算符。当你想修改数组元素的值而不想生成新数组时,就可以使用它们
a = np.arange(5)
a += 3
print(a) # [3 4 5 6 7]
a -= 2
print(a) # [1 2 3 4 5]
a *= 3
print(a) # [ 3 6 9 12 15]
2.4 唯一化与集合运算
NumPy提供了一些针对一维ndarray的基本集合运算。最常用的就是np.unique了,它用于找出数组中的唯一值并返回已排序的结果。
a = np.array([[3,7,5,5,5,3,9,9]])
# a中的唯一元素
print(np.unique(a)) # [3 5 7 9]
此外,还有如下集合运算函数
函数 | 描述 |
---|---|
intersect1d(x,y) | 计算x和y中的公共元素,并返回有序结果 |
union1d(x,y) | 计算x和y的并集,并返回有序结果 |
in1d(x,y) | 得到一个表示“x的元素是否包含于y”的布尔型数组 |
setdiff1d(x,y) | 集合的差,即元素在x中且不在y中 |
setxor1d(x,y) | 集合的对称差,即存在于一个数组中但不同时存在于两个数组中的元素 |
代码演示:
a = np.array([3,8,4,6,8,5])
b = np.array([1,2,6,5,8])
# a与b的公共元素
print(np.intersect1d(a,b)) # [5 6 8]
# a与b的并集
print(np.union1d(a,b)) # [1 2 3 4 5 6 8]
# a的每个元素是否存在与b中
print(np.in1d(a,b)) # [False True False True True True]
# a与b的差
print(np.setdiff1d(a,b)) # [3 4]
# a与b的对称差
print(np.setxor1d(a,b)) # [1 2 3 4]
3. 矩阵
3.1 创建矩阵
一般我们可以通过np.mat()或者np.matrix()方法来创建矩阵
m = np.mat([[1,2,3],[4,5,6]])
print(type(m)) # numpy.matrix
m2 = np.matrix([[1,2,3],[4,5,6]])
print(type(m2)) # numpy.matrix
此外,NumPy中包含了一个矩阵库numpy.matlib,该模块中的函数返回的是一个矩阵,而不是 ndarray 对象。
函数 | 描述 |
---|---|
matlib.empty() | 返回一个新的矩阵 |
matlib.zeros() | 创建一个以 0 填充的矩阵 |
matlib.ones() | 创建一个以 1 填充的矩阵 |
matlib.eye() | 返回一个对角线元素为 1,其他位置为零的矩阵 |
matlib.identity() | 返回给定大小的单位矩阵 |
matlib.rand() | 函数创建一个给定大小的矩阵,数据是随机填充的 |
代码演示:
print("2*3矩阵:\n",np.matlib.empty((2,3)))
print("2*3矩阵:\n",np.matlib.zeros((2,3)))
print("2*3矩阵:\n",np.matlib.ones((2,3)))
print("3*4矩阵:\n",np.matlib.eye(n = 3, M = 4, k = 0, dtype = float))
print("大小为 5,类型为浮点型的矩阵:\n",np.matlib.identity(5, dtype = float))
print("3*3随机填充数据矩阵:\n",np.matlib.rand(3,3))
输出结果
2*3矩阵:
[[4.24399158e-3148.48798317e-3141.27319747e-313]
[1.69759663e-3132.12199579e-3132.54639495e-313]]
2*3矩阵:
[[0.0.0.]
[0.0.0.]]
2*3矩阵:
[[1.1.1.]
[1.1.1.]]
3*4矩阵:
[[1.0.0.0.]
[0.1.0.0.]
[0.0.1.0.]]
大小为 5,类型为浮点型的矩阵:
[[1.0.0.0.0.]
[0.1.0.0.0.]
[0.0.1.0.0.]
[0.0.0.1.0.]
[0.0.0.0.1.]]
3*3随机填充数据矩阵:
[[0.681549250.83888520.2949826 ]
[0.963048090.279172410.08094938]
[0.653578310.24164510.93637365]]
3.2 矩阵运算
Numpy提供了线性代数函数库linalg,该库包含了线性代数所需的所有功能
函数 | 描述 |
---|---|
diag() | 返回方阵的对角线元素,或将一维数组转换为方阵 |
dot() | 返回两个数组的点积 |
inner() | 两个数组的内积 |
matmul() | 两个数组的矩阵积 |
linalg.det() | 计算矩阵的行列式 |
linalg.inv() | 计算矩阵的乘法逆矩阵 |
trace() | 计算对角线元素的和 |
linalg.eig() | 计算方阵的本征值和本征向量 |
linalg.pinv() | 计算矩阵的Moore-Penrose伪逆qr计算QR分解 |
linalg.solve() | 求解线性矩阵方程Ax=b,其中A为一个方阵 |
linalg.svd() | 计算奇异值分解(SVD) |
linalg.lstsq() | 计算Ax=b的最小二乘解 |
代码演示:
a = np.array([1,2,3])
b = np.array([[2,3,4],[5,8,9],[9,6,1]])
'''array是一个一维数组时,返回一个以一维数组为对角线元素的矩阵'''
print(np.diag(a))
# 输出结果:
[[100]
[020]
[003]]
'''array是一个二维矩阵时,结果输出矩阵的对角线元素'''
print(np.diag(b))
# 输出结果:[2 8 1]
a = np.array([2,5,3,4])
b = np.array([1,8,2,2])
'''a和b都是一个一维数组时,返回向量的点积'''
print(np.dot(a,b))
# 输出结果:56
a = np.array([[1,2],[3,4]])
b = np.array([[2,8],[3,2]])
'''a和b都是二维矩阵时,返回矩阵的乘法运算'''
print(np.dot(a,b))
# 输出结果:
[[ 812]
[1832]]
'''计算矩阵a和b的内积'''
print(np.inner(a,b))
# 输出结果:
[[187]
[3817]]
'''计算矩阵积,这里与dot一样'''
print(np.matmul(a,b))
# 输出结果:
[[ 812]
[1832]]
'''计算行列式'''
print(np.linalg.det(a))
# 输出结果:-2.0000000000000004
'''计算a的逆'''
print(np.linalg.inv(a))
# 输出结果:
[[-2.1. ]
[ 1.5-0.5]]
'''计算a对角线的和'''
print(np.trace(a))
# 输出结果:5
'''计算本征值和本征向量'''
print(np.linalg.eig(a))
# 输出结果:
(array([-0.37228132, 5.37228132]), array([[-0.82456484, -0.41597356],
[ 0.56576746, -0.90937671]]))
'''奇异分解'''
print(np.linalg.svd(a))
# 输出结果:
(array([[-0.40455358, -0.9145143 ],
[-0.9145143 , 0.40455358]]), array([5.4649857 , 0.36596619]), array([[-0.57604844, -0.81741556],
[ 0.81741556, -0.57604844]]))
'''计算a 的伪逆矩阵'''
print(np.linalg.pinv(a))
# 输出结果:
[[-2.1. ]
[ 1.5-0.5]]
'''求解ax=b'''
print(np.linalg.solve(a,b))
# 输出结果:
[[ -1.-14. ]
[ 1.511. ]]
1. 函数使用
1.1 通用函数
通用函数通常称为ufunc,它对数组中的各个元素逐一进行操作。常用的通用函数有以下几种
函数 | 描述 |
---|---|
abs() | 计算整数、浮点数或复数的绝对值 |
sqrt() | 计算各元素的平方根 |
square() | 计算各元素的平方 |
exp() | 计算各元素的e(自然对数的底)的幂次方 |
around() | 对各元素保留x位小数位 |
log、log10、log2、loglp | 分别为自然对数(底数为e)、底数为10的1og、底数为2的log、log(1+x) |
cos、cosh、sin、sinh、tan、tanh | 普通型和双曲型三角函数 |
arccos、arccosh、arcsin | 反三角函数 |
sign | 返回各元素的正负号:1(正数)、0(零)、-1(负数) |
ceil | 向上取整,即大于等于该值的最小整数 |
floor | 向下取整,即小于等于该值的最大整数 |
rint | 将各元素值四舍五入到最接近的整数,保留dtype |
isnan | 判断值是否为NaN |
isfinite、isinf | 分别判断值是否是有穷的、无穷的 |
通用函数分别处理输入数组的每个元素,生成的结果组成一个新的输出数组。
a = np.array([1.0,5.55,123,-0.567,25.532])
print ('原数组:',a) # 原数组:[ 1. 5.55 123. -0.567 25.532]
print('绝对值:',np.abs(a)) # 绝对值:[ 1. 5.55 123. 0.567 25.532]
print('平方根:',np.sqrt(a)) # 平方根:[ 1. 2.3558438 11.09053651 nan 5.05291995]
print('平方:',np.square(a)) # 平方:[1.00000000e+00 3.08025000e+01 1.51290000e+04 3.21489000e-01 6.51883024e+02]
print ('保留一位小数:',np.around(a, decimals = 1)) # 保留一位小数:[ 1. 5.6 123. -0.6 25.5]
print ('向下取整:',np.floor(a)) # 向下取整:[ 1. 5. 123. -1. 25.]
print ('向上取整:',np.ceil(a)) # 向上取整:[ 1. 6. 123. -0. 26.]
# 指数运算
x = [1, 2, 3]
print("x =", x) # x = [1, 2, 3]
print("e^x =", np.exp(x)) # e^x = [ 2.71828183 7.3890561 20.08553692]
print("2^x =", np.exp2(x)) # 2^x = [2. 4. 8.]
print("3^x =", np.power(3, x)) # 3^x = [ 3 9 27]
print("ln(x) =", np.log(x)) # ln(x) = [0. 0.69314718 1.09861229]
print("log2(x) =", np.log2(x)) # log2(x) = [0. 1. 1.5849625]
print("log10(x) =", np.log10(x)) # log10(x) = [0. 0.30103 0.47712125]
# 三角函数
theta = np.linspace(0, np.pi, 3)
print("theta = ", theta) # theta = [0. 1.57079633 3.14159265]
print("sin(theta) = ", np.sin(theta)) # sin(theta) = [0.0000000e+00 1.0000000e+00 1.2246468e-16]
print("cos(theta) = ", np.cos(theta)) # cos(theta) = [ 1.000000e+00 6.123234e-17 -1.000000e+00]
print("tan(theta) = ", np.tan(theta)) # tan(theta) = [ 0.00000000e+00 1.63312394e+16 -1.22464680e-16]
x = [-1, 0, 1]
print("x = ", x) # x = [-1, 0, 1]
print("arcsin(x) = ", np.arcsin(x)) # arcsin(x) = [-1.57079633 0. 1.57079633]
print("arccos(x) = ", np.arccos(x)) # arccos(x) = [3.14159265 1.57079633 0. ]
print("arctan(x) = ", np.arctan(x)) # arctan(x) = [-0.78539816 0. 0.78539816]
1.2 统计函数
NumPy 提供了很多统计函数,用于从数组中查找最小元素,最大元素,百分位,标准差和方差等。
函数 | 描述 |
---|---|
min() | 求最小值 |
amin() | 用于计算数组中的元素沿指定轴的最小值。 |
max() | 求最大值 |
amax() | 用于计算数组中的元素沿指定轴的最大值。 |
ptp() | 函数计算数组中元素最大值与最小值的差(最大值 - 最小值)。 |
percentile(a, q, axis) | 百分位数是统计中使用的度量,表示小于这个值的观察值的百分比。 |
sum() | 计算元素和 |
prod() | 计算元素乘积 |
std() | 计算标准差 |
var() | 计算方差 |
any() | 评估任何元素是否为真 |
all() | 评估所有元素是否为真 |
median() | 计算数组 a 中元素的中位数(中值) |
mean() | 返回数组中元素的算术平均值 |
average() | 根据在另一个数组中给出的各自的权重计算数组中元素的加权平均值 |
cumsum() | 所有元素的累计和 |
cumprod() | 所有元素的累计积 |
代码演示:
a = np.array([[3,7,5],[8,4,3],[2,4,9]])
print(a)
print ("数组中的最小值:",np.amin(a),np.min(a))
print ("每行的最小值:",np.amin(a,1))
print ("每列的最小值:",np.amin(a,0))
print ("数组中的最大值:",np.amax(a),np.max(a))
print ("每行的最大值:",np.amax(a, axis = 1))
print ("每列的最大值:",np.amax(a, axis = 0))
print ("每行最大值与最小值的差:",np.ptp(a,axis = 1))
print ("在横行上求50% 的分位数:",np.percentile(a, 50,axis = 1))
print ("在横行上求中位数(中值):",np.median(a, axis = 1))
print ("在横行上求算术平均值:",np.mean(a, axis = 1))
print ("所有元素的累计和:",np.cumsum(a))
print ("所有元素的累计积:",np.cumprod(a))
输出结果
[[375]
[843]
[249]]
数组中的最小值:22
每行的最小值:[332]
每列的最小值:[243]
数组中的最大值:99
每行的最大值:[789]
每列的最大值:[879]
每行最大值与最小值的差:[457]
在横行上求50% 的分位数:[5.4.4.]
在横行上求中位数(中值):[5.4.4.]
在横行上求算术平均值:[5.5.5.]
所有元素的累计和:[ 31015232730323645]
所有元素的累计积:[ 3211058403360100802016080640725760]
1.3 排序函数
函数 | 描述 |
---|---|
sort() | 返回输入数组的排序数组 |
argsort() | 返回数组值从小到大的索引值 |
argmin() | 沿给定轴返回最小元素的索引 |
argmax() | 沿给定轴返回最大元素的索引 |
代码演示:
a = np.array([[3, 12, 6],[1, 7, 3], [4, 2, 0]])
print(a)
print(np.sort(a)) # 将每一行的元素按从小到大排列
print(np.argsort(a)) # 返回每一行数组值从小到大的索引值
print(np.argmin(a,axis=0)) # 返回每一列最小值的索引
print(np.argmax(a,axis=0)) # 返回每一列最大值的索引
print(np.argmin(a,axis=1)) # 返回每一行最小值的索引
print(np.argmax(a,axis=1)) # 返回每一行最大值的索引
输出结果
# a
[[ 3126]
[ 173]
[ 420]]
# np.sort(a)
[[ 3612]
[ 137]
[ 024]]
# np.argsort(a)
[[021]
[021]
[210]]
# np.argmin(a,axis=0)
[122]
# np.argmax(a,axis=0)
[200]
# np.argmin(a,axis=1)
[002]
# np.argmax(a,axis=1)
[110]
1.4 条件函数
函数 | 描述 |
---|---|
extract() | 根据某个条件从数组中抽取元素,返回满足条件的元素 |
isnan() | 判断NaN值,返回一个布尔型数组 |
nonzero() | 返回输入数组中非零元素的索引 |
where() | 返回输入数组中满足给定条件的元素索引 |
代码演示:
a = np.array([[3, 12, 6],[1, 7, 3], [4, 2, 0]])
# 找出大于3的元素
print(np.extract(a>3,a))
b = np.array([[1,np.nan,2],[3,4,np.nan]])
# 判断空值
print(np.isnan(b))
c = np.array([[2,6,0],[0,0,7]])
# 返回非0值的索引,其输出结果第一个数组表示行索引,第二个数组表示列索引
print(np.nonzero(c))
d = np.array([[2,4],[5,8],[1,7]])
# 返回大于3的元素索引,其输出结果第一个数组表示行索引,第二个数组表示列索引
print(np.where(d>3))
输出结果
# np.extract(a>3,a)
[12674]
# np.isnan(b)
[[FalseTrueFalse]
[FalseFalseTrue]]
# np.nonzero(c)
(array([0, 0, 1], dtype=int64), array([0, 1, 2], dtype=int64))
# np.where(d>3)
(array([0, 1, 1, 2], dtype=int64), array([1, 0, 1, 1], dtype=int64))
2 切片与索引
2.1 索引
与list的索引操作一样,ndarray数组可以基于下标进行索引操作
# 索引
x = np.array([1, 2, 3])
print ("x[0]: ", x[0]) # 取第一个位置元素
x[0] = 0# 修改第一个位置元素
print ("x: ", x)
输出结果
x[0]: 1
x: [023]
2.2 切片
对于ndarry对象,可使用slice(start,stop,step)函数来进行切片
a = np.arange(10)
print(a) # 结果:[0 1 2 3 4 5 6 7 8 9]
# 从索引2开始到索引7停止(不包含7),间隔为2
s = slice(2,7,2) # 结果:[2 4 6]
print (a[s])
关于数组的切片,我们更常使用':'冒号来进行切片
-
如果只放置一个参数,如 [1],将返回与该索引相对应的单个元素
-
如果为 [1:],表示从该索引[1]开始以后的所有项都将被提取
-
如果使用了两个参数,如 [1:3],那么则提取两个索引(不包括停止索引)之间的项
x = np.array([[1,2,3,4], [5,6,7,8], [9,10,11,12]])
print (x[:, 1]) # 取每一行中索引为1(即第二个位置)的元素
print (x[0, :]) # 取索引为0(即第一行)的所有元素
print (x[:3, 1:3]) # 取行索引为0,1,2,列索引为1,2的元素
输出结果
# x[:, 1]
[ 2610]
# x[0, :]
[1234]
# x[:3, 1:3]
[[ 23]
[ 67]
[1011]]
2.3 高级索引
NumPy比一般的Python序列提供更多的索引方式。除了用整数和切片的索引外,数组还能通过其他方式来进行索引。
(1)整数索引
传入一个整数列表来对数组进行索引
x = np.array([[1,5,8,4],[2,4,8,3],[3,6,1,9]])
print(x[[1,2],[0,3]]) # 取索引为[1,0]和[2,3]的元素
# 输出结果:
[29]
(2)布尔索引
传入一个布尔类型列表来对数组进行索引
x = np.array([[1,5,8,4],[2,4,8,3],[3,6,1,9]])
print(x>3)
print(x[x>3]) # 取出大于3的元素
# 输出结果:
# x>3
[[FalseTrueTrueTrue]
[FalseTrueTrueFalse]
[FalseTrueFalseTrue]]
# x[x>3]
[5844869]
(3)按照条件返回索引
常使用到的条件函数方法如下
-
numpy.argmax() 函数沿给定轴返回最大元素的索引
-
numpy.argmin() 函数沿给定轴返回最小元素的索引
-
numpy.nonzero() 函数返回输入数组中非零元素的索引
-
numpy.where() 函数返回输入数组中满足给定条件的元素的索引
通过这些条件函数,我们可以很方便的获取到符合条件的元素索引
a = np.array([[30,40,70],[80,20,10],[50,90,60]])
print ("数组展开最大元素的索引:",np.argmax(a))
print ("数组按列最大元素的索引:",np.argmax(a, axis = 0))
print ("数组按行最大元素的索引:",np.argmax(a, axis = 1))
print ("数组展开最大元素的索引:",np.argmin(a))
print ("数组按列最大元素的索引:",np.argmin(a, axis = 0))
print ("数组按行最大元素的索引:",np.argmin(a, axis = 1))
print ("数组中非零元素的索引:",np.nonzero (a))
print ("数组中大于50的索引:",np.where(a > 50))
print ('使用这些索引来获取满足条件的元素:',a[np.where(a > 50)])
输出结果
数组展开最大元素的索引:7
数组按列最大元素的索引:[120]
数组按行最大元素的索引:[201]
数组展开最大元素的索引:5
数组按列最大元素的索引:[011]
数组按行最大元素的索引:[020]
数组中非零元素的索引:(array([0, 0, 0, 1, 1, 1, 2, 2, 2], dtype=int64), array([0, 1, 2, 0, 1, 2, 0, 1, 2], dtype=int64))
数组中大于50的索引:(array([0, 1, 2, 2], dtype=int64), array([2, 0, 1, 2], dtype=int64))
使用这些索引来获取满足条件的元素:[70809060]
3. 数组操作
3.1 形状变换
一般我们常用reshape方法来修改数组的形状
a = np.arange(8)
b = a.reshape(4,2)
print(b)
# 输出结果
[[01]
[23]
[45]
[67]]
此外,还可以使用ravel()函数和flatten()函数来进行扁平化操作
print(b.ravel()) # [0 1 2 3 4 5 6 7]
print(b.flatten()) # [0 1 2 3 4 5 6 7]
从上面的例子看出这两个函数实现的功能是一样的,但是在平时使用时,推荐使用flatten函数,这是因为flatten()分配了新的内存,但ravel()返回的是一个数组的视图。如果我们对视图进行修改,那么原数组也会修改。
a = np.arange(6).reshape(3,2)
b = np.arange(1,7).reshape(3,2)
c = a.ravel()
d = b.flatten()
print(c)
print(d)
c[0]=100
d[0]=100
print(a) # 对c修改时,a也发生了变化
print(b) # 对d修改时,b不会变化
输出结果
# c
[012345]
# d
[123456]
# a
[[1001]
[ 23]
[ 45]]
# b
[[12]
[34]
[56]]
在矩阵运算中,还可以使用transpose()函数实现矩阵转置
a = np.arange(6).reshape(3,2)
print(a) # 转置前
print(np.transpose(a)) # 转置后
## 输出结果
# 转置前
[[01]
[23]
[45]]
# 转置后
[[024]
[135]]
当然其实还有更简单的方法,那就是直接使用ndarray.T方法
a = np.arange(6).reshape(3,2)
print(a.T)
# 输出结果
[[024]
[135]]
3.2 数组合并
Numpy支持将多个数组整合在一起形成一个新的数组,可以通过以下函数来实现该功能
-
vstack():垂直入栈操作,即行添加
-
hstack():水平入栈操作,即列添加
-
concatenate():沿指定轴axis连接相同形状的两个或多个数组
代码演示:
a = np.array([[1,2],[3,4]])
b = np.array([[5,6],[7,8]])
'''沿轴 0 连接两个数组'''
print (np.concatenate((a,b)))
# 输出结果
[[12]
[34]
[56]
[78]]
'''沿轴 1 连接两个数组'''
print (np.concatenate((a,b),axis = 1))
# 输出结果
[[1256]
[3478]]
print(np.vstack([a,b]))
# 输出结果
[[12]
[34]
[56]
[78]]
print(np.hstack([a,b]))
# 输出结果
[[1256]
[3478]]
3.3 数组拆分
数组拆分就是指将一个数组分成几部分,其切分函数有
-
hsplit():水平切分
-
vsplit():垂直切分
-
split():按指定轴切分 代码演示:
a = np.arange(16).reshape(4,4)
[a1,a2]=np.hsplit(a,2)
print(a1)
print(a2)
# a1
[[ 01]
[ 45]
[ 89]
[1213]]
# a2
[[ 23]
[ 67]
[1011]
[1415]]
[a3,a4]=np.vsplit(a,2)
print(a3)
print(a4)
# a3
[[0123]
[4567]]
# a4
[[ 891011]
[12131415]]
split函数要复杂一些,它可以将数组分为几个不对称的部分,除了传入数组作为参数外,还得指定被切分部分的索引
[a1,a2,a3] = np.split(a,[1,3],axis=1)
# a1
[[ 0]
[ 4]
[ 8]
[12]]
# a2
[[ 12]
[ 56]
[ 910]
[1314]]
# a3
[[ 3]
[ 7]
[11]
[15]]
3.4 数组元素的添加与删除
可以使用以下函数来对数组进行添加和删除操作
函数 | 描述 |
---|---|
append() | 在数组的末尾添加值。 |
insert() | 沿给定轴axis及索引位置插入值 |
delete() | 从输入数组arr中删除指定子数组 |
代码演示:
a = np.array([[1,2,3],[4,5,6]])
print (np.append(a, [7,8,9]))
# 输出结果
[123456789]
a = np.array([[1,2],[3,4],[5,6]])
print (np.insert(a,1,[11],axis = 0))
# 输出结果
[[ 12]
[1111]
[ 34]
[ 56]]
a = np.arange(12).reshape(3,4)
print (np.delete(a,2,axis = 1))#删除第三列
# 输出结果
[[ 013]
[ 457]
[ 8911]]