numpy是Numerical Python的简写,是python数值计算的基石。它是目前Python数值计算中最为重要的基础包。 Numpy的重要功能:
对于一个100万的数据来说,使用numpy进行操作要比用python直接操作快10到100倍
import numpy as np #这是约定俗成的导入numpy的方式,建议你也这样做
list1 = np.arange(1000000)
list2 = list(range(1000000))
%time for _ in range(10):list3 = list1 * 2
CPU times: user 12.5 ms, sys: 9.99 ms, total: 22.5 ms Wall time: 23.6 ms
%time for _ in range(10):list4 = [x * 2 for x in list2]
CPU times: user 608 ms, sys: 207 ms, total: 816 ms Wall time: 838 ms
这个例子可以看出明显的差距
Numpy的核心特征之一就是N-维数组对象-ndarray。ndarry是Python中一个快速、灵活的大型数据集容齐。数组允许你使用列斯与标量的操作语法在整块数据上进行数学计算。 下面是使用Numpy生成小的随机数组
import numpy as np
data = np.random.randn(2,3)
print(data)
[[ 1.44387396 -0.25442857 1.13255162] [ 0.53088762 1.39146013 0.56735466]]
print(data * 10)
[[14.43873964 -2.5442857 11.32551616] [ 5.30887617 13.91460135 5.67354659]]
print(data + data)
[[ 2.88774793 -0.50885714 2.26510323] [ 1.06177523 2.78292027 1.13470932]]
ndarry包含几个常用的属性
- T: 返回数组的转置
- shape: 返回数组每一维度的数量
- dtype: 返回数组的数据类型
- size: 返回数组中的数据数量
- ndim: 返回数组的维数
print(data.T)
print(data.shape)
print(data.dtype)
print(data.size)
print(data.ndim)
[[ 1.44387396 0.53088762] [-0.25442857 1.39146013] [ 1.13255162 0.56735466]] (2, 3) float64 6 2
生成ndarry最简单的方式就是使用array函数。 np.array函数会自动推断数组的数据类型
data1 = [6,7.5,8,0,1]
arr1 = np.array(data1)
print(arr1)
print(arr1.dtype)
[6. 7.5 8. 0. 1. ] float64
同等长度的列表,将会自动转换成多维数组
data2 = [[1,2,3,4],[4,5,6,7]]
arr2 = np.array(data2)
print(arr2)
print(arr2.dtype)
[[1 2 3 4] [4 5 6 7]] int64
还有一些新的函数可以创建新的数组
print(np.zeros(10))
print(np.zeros((2,3)))#⚠️注意这里要有括号,传入一个元组
print(np.ones(5))
[0. 0. 0. 0. 0. 0. 0. 0. 0. 0.] [[0. 0. 0.] [0. 0. 0.]] [1. 1. 1. 1. 1.]
类型 | 类型代码 | 描述 |
---|---|---|
int8,unit8 | i1,u1 | 有符号和无符号的8位整数 |
int16,unit16 | i2,u2 | 有符号和无符号的16位整数 |
int32,unit32 | i4,u4 | 有符号和无符号的32位整数 |
int64,unit64 | i8,u8 | 有符号和无符号的64位整数 |
float16 | f2 | 半精度浮点数 |
float32 | f4 | 标准单精度浮点数,兼容C语言float |
float64 | f8 | 标准双精度浮点数,兼容c语言double和python float |
float128 | f16 | 拓展精度浮点数 |
bool | ? | 布尔值,存储True或False |
string_ | S | 字符串类型 |
import numpy as np
arr = np.array([1,2,3,4,5])
print(arr.dtype)
int64
float_arr = arr.astype(np.float64)
print(float_arr.dtype)
float64
在上面这个例子中,整数被转换为浮点数,使用了astype()
函数,如果把浮点数转换为整数,则小数点后的部分被消除。
数组最重要的特征就是允许你进行批量操作而不需要使用for循环。称此种特征为向量化
import numpy as np
arr = np.array([[1.,2.,3.],[4.,5.,6.]])
print(arr)
print("\n", arr *arr)
print("\n", arr -arr)
print("\n", 1 / arr)
print("\n", arr ** 0.5)
[[1. 2. 3.] [4. 5. 6.]] [[ 1. 4. 9.] [16. 25. 36.]] [[0. 0. 0.] [0. 0. 0.]] [[1. 0.5 0.33333333] [0.25 0.2 0.16666667]] [[1. 1.41421356 1.73205081] [2. 2.23606798 2.44948974]]
还可以比较两个数组,会返回比较后的布尔值
arr2 = np.array([[0.,4.,1.],[7.,2.,12.]])
print(arr2)
print("\n", arr2 > arr)
[[ 0. 4. 1.] [ 7. 2. 12.]] [[False True False] [ True False True]]
import numpy as np
#numpy的arange类似于python的range函数
arr = np.arange(10)
print(arr)
print(arr[5])#称为索引
print(arr[5:8])#称为切片
arr[5:8] = 10
print(arr)
[0 1 2 3 4 5 6 7 8 9] 5 [5 6 7] [ 0 1 2 3 4 10 10 10 8 9]
这是在一维数组上的切片操作,需要⚠️注意的是当对数组进行操作时会直接对原数组进行修改。
import numpy as np
arr = np.array([[1,2,3],[4,5,6],[7,8,9]])
print(arr)
print("\n", arr[0])
print("\n",arr[0][2])
[[1 2 3] [4 5 6] [7 8 9]] [1 2 3] 3
对于一个多维数组,一次切片会返回一维数组,若想精确的选择某个值需要对其再进行索引
数组也可以与python中的列表对象类似,通过切片对其中的数据进行取值
arr = [0,1,2,3,4,5,6,7,8,9]
print(arr[1:5])
print(arr[:4])
print(arr[:-1])
[1, 2, 3, 4] [0, 1, 2, 3] [0, 1, 2, 3, 4, 5, 6, 7, 8]
对于多维数组来说,可以通过多级的索引或切片进行取值,如图所示:
import numpy as np
arr = np.array([[1,2,3],[4,5,6],[7,8,9]])
print(arr[:, 1])
print("\n")
print(arr[0:2, 2])
print("\n")
print(arr[1, 0:2])
print("\n")
print(arr[0:2, 0:2])
[2 5 8] [3 6] [4 5] [[1 2] [4 5]]
与线性代数中理解的矩阵转置一样,numpy中提供了方便的数组转置方法
arr = np.arange(15).reshape((3,5))
print(arr)
print("\n")
print(arr.T)#此为数组的转置
[[ 0 1 2 3 4] [ 5 6 7 8 9] [10 11 12 13 14]] [[ 0 5 10] [ 1 6 11] [ 2 7 12] [ 3 8 13] [ 4 9 14]]
对矩阵进行计算时会涉及一些特殊的操作,比如计算矩阵的内积,我们可以使用np.dot方法
print(np.dot(arr.T, arr))
[[125 140 155 170 185] [140 158 176 194 212] [155 176 197 218 239] [170 194 218 242 266] [185 212 239 266 293]]
一元通用函数
函数名 | 描述 | |
---|---|---|
abs ,fabs |
逐元素地计算整数,浮点数或负数的绝对值 | |
sqrt |
计算每个元素的平方根 | |
square |
计算每个元素的平方 | |
exp |
计算每个元素的自然指数值ex | |
log ,log10 ,log2 |
分别对应自然对数,对数10为底,对数2为底 | |
sign |
计算每个元素的符号值 |
arr = np.arange(1, 10)
print(arr)
print("\n")
print(np.sqrt(arr))
print("\n")
print(np.square(arr))
print("\n")
print(np.exp(arr))
print("\n")
print(np.log10(arr))
print("\n")
print(np.sign(arr))
[1 2 3 4 5 6 7 8 9] [1. 1.41421356 1.73205081 2. 2.23606798 2.44948974 2.64575131 2.82842712 3. ] [ 1 4 9 16 25 36 49 64 81] [2.71828183e+00 7.38905610e+00 2.00855369e+01 5.45981500e+01 1.48413159e+02 4.03428793e+02 1.09663316e+03 2.98095799e+03 8.10308393e+03] [0. 0.30103 0.47712125 0.60205999 0.69897 0.77815125 0.84509804 0.90308999 0.95424251] [1 1 1 1 1 1 1 1 1]
二元通用函数
函数名 | 描述 | |
---|---|---|
add | 将数组对应元素相加 | |
multiply | 将数组对应元素相乘 | |
divide,floor_fivide | 初或整除 | |
power | 将第二个数组元素作为第一个数组元素的幂 | |
maximum | 逐个计算元素的最大值 | |
minimum | 逐个计算元素的最小值 | |
mode | 求元素的模 |
x = np.random.randn(8)
y = np.random.randn(8)
print(x)
print("\n")
print(y)
print("\n")
print(np.maximum(x,y))
print("\n")
print(np.multiply(x,y))
[-2.81931681 -1.16594766 1.25560557 -0.53089508 -0.88346508 -0.69976644 0.18584147 -0.78739778] [ 1.10865854 0.07394118 0.18840718 -0.56140484 0.50711533 -0.60786824 -0.24535454 -2.96499746] [ 1.10865854 0.07394118 1.25560557 -0.53089508 0.50711533 -0.60786824 0.18584147 -0.78739778] [-3.12565966 -0.08621154 0.23656511 0.29804707 -0.44801869 0.4253658 -0.04559705 2.33463243]
numpy中提供了大量的线性代数操作,这些函数是使用标准的线性代数库来实现的,numpy的线性代数操作都存在于linalg中。
函数名 | 描述 | |
---|---|---|
diag |
将一个方针的对角元素作为一维数组返回,或将一维数组转换成一个方阵 | |
dot |
计算矩阵的点乘 | |
trace |
计算对角元素的和 | |
det |
计算矩阵的行列式 | |
eig |
计算方阵的特征值和特征向量 | |
inv |
计算方阵的逆矩阵 |
import numpy as np
x = np.array([[1.,2.,3.], [4.,5.,6.]])
y = np.array([[6.,23.],[-1,7],[8,7]])
print(x)
print("\n")
print(y)
print("\n")
print(x.dot(y))
print("\n")
z = x.dot(x.T)
print(z)
print("\n")
print("diag: ", np.diag(z))
print("trace: ",z.trace())
print("det: ", np.linalg.det(z))
print("dig: ", np.linalg.eig(z))
print("inv: ", np.linalg.inv(z))
[[1. 2. 3.] [4. 5. 6.]] [[ 6. 23.] [-1. 7.] [ 8. 7.]] [[ 28. 58.] [ 67. 169.]] [[14. 32.] [32. 77.]] diag: [14. 77.] trace: 91.0 det: 54.00000000000001 dig: (array([ 0.59732747, 90.40267253]), array([[-0.92236578, -0.3863177 ], [ 0.3863177 , -0.92236578]])) inv: [[ 1.42592593 -0.59259259] [-0.59259259 0.25925926]]
numpy.random填补了python内建的random的不足,使用numpy可以高效的生成多种概率分布下的完整样本值数组。
函数名 | 描述 | |
---|---|---|
seed |
向随机数生成器传递随机状态种子 | |
shuffle |
随机排列一个序列 | |
rand |
从均匀分布中抽取样本 | |
randint |
根据给定的范围抽取随机整数 | |
randn |
从均值0方差1的正态分布中抽取样本 | |
normal |
从正态分布中抽取样本 |
samples = np.random.normal(size=(4,4))
print(samples)
[[-0.44935052 1.36724432 -0.31976099 0.90308154] [ 1.04837402 -0.87623288 1.93919589 1.11932443] [-0.73634142 -0.71623403 -1.94616623 0.82323579] [-1.90485977 0.50994768 -0.06533462 -0.65938636]]
sample = np.arange(1, 10)
print(sample)
[1 2 3 4 5 6 7 8 9]