Numpy的基本操作(笔记)

这里记一下我看视频时所学到的东西作为一个笔记主要是为了学机器学习而做的基础准备,有错误的地方还大家请指出

0.Numpy导入

import numpy as np
print(np.__version__) # 查看版本

1. 数组的创建和属性

创建
lst = [1, 2, 3]
arr = np.array(lst) # 通过传入列表创建一个np数组

arr = np.zeros(shape=(5, 2), dtype=int)# 创建一个大小为5 X 2的int类型的0数组

arr = np.ones(shape=(5, 2), dtype=int)# 创建一个大小为5 X 2的int类型的0数组

arr = np.full(fill_value=10, shape=(3, 5))# 创建一个大小为3 X 5,值全为10的数组

arr = np.arange(1, 5)# 创建一个数组为[1,2,3,4]
# 这里arange与Py的range相似,这里的第三个参数可以是步长,而且步长可以是浮点数

arr = np.linspace(1, 10, 10)
'''
生成数组:
[ 1.  2.  3.  4.  5.  6.  7.  8.  9. 10.]
linspace方法是从区间[1,10]内截等长出个数,前连个参数是区间,最后一个是截出来的个数
'''

arr = np.random.randint(1, 10, size=(2, 5))
'''
在[1, 10)区间内取整数随机生成一个大小为2 X 5的数组
这里size相当于shape,可以是一维也可以是多维
'''
np.random.seed(100)# 设置随机数种子

arr = np.random.random((2, 5))
'''
在[0, 1)区间内随机取浮点数生成一个大小为2 X 5的数组
其中所有数都是在此区间内均匀分布,参数只有一个size
'''

arr = np.random.normal(size=(2, 5))
'''
生成一个符合正态分布大小为2 X 5的浮点数数组
'''

arr = np.random.normal(10, 100, size=(2, 5))
'''
生成均值为10,方差为100,大小为2 X 5 的数组
'''
属性
print(arr.dtype) # 查看数组的类型
print(arr.ndim) # 查看维度
print(arr.shape)# 查看数组的形状
print(arr.size) # 查看元素个数
'''
array有对应的类型,只能存对应类型的值
类似于C的数组,如果给一个整数数组传入小数的值会强制转型
字符串也会,如果转不了就会报错
'''
arr = arr.astype(int)
'''
对arr进行强制转型
'''

2. 数据访问,变形操作

之后的数组统称为矩阵或者向量

数据访问
arr = np.arange(1, 10).reshape(3, 3)
'''
创建一个3x3的演示矩阵
这里reshape是变形操作,在下方有记录
[[1 2 3]
 [4 5 6]
 [7 8 9]]
'''

print(arr[2][2])
print(arr[-1][-2])
print(arr[1,2])
'''
输出结果为
9
8
6
前两个可以看到,对于使用索引数据访问时和Py的无差别
最后一个实际上就是访问了(1,2)这个元素
'''
print(arr[:, 2],end='\n-----')
print(arr[0:2, 1:3])
'''
结果:
[3 6 9]
-----
[[2 3]
 [5 6]]
这里实际上相当于切片操作了也就说是
arr[行的切片,列的切片]
就是先按行的切片取,然后再按列的切片取
再举几个例子:
'''
例子:
print(arr[::2, 2], end='\n-----\n')
print(arr[1, :])
'''
输出:
[3 9]
-----
[4 5 6]
需要注意的是,取出来的的子矩阵是原矩阵的引用,也就是改子矩阵的值会影响原矩阵
如果想创建一个新的矩阵的话就要使用copy方法
'''
subarr = arr[1,:].copy()
# copy方法独立创建一个子矩阵此矩阵不再与原矩阵有关系
变形
arr = np.arange(1, 10)
print(arr, end='\n\n')
arr = np.reshape(arr, (3, 3))
print(arr, end='\n\n')
arr = np.reshape(arr, (3, -1))
print(arr, end='\n\n')
'''
输出结果:
[1 2 3 4 5 6 7 8 9]

[[1 2 3]
 [4 5 6]
 [7 8 9]]
 可以看到reshape方法改变了矩阵的形状,调用reshape时可以直接对矩阵调用也可以把矩阵当参数调用,后者调用时不改变原矩阵的值
 当传入形状时,如果填-1则会被认作根据另个参数来确定,比如填(3, -1),总元素个数为9个,一共变成3行列根据行决定,也就是9 // 3列,如果不能整除就会报错
'''

3. 分割与拼接

拼接

concatenate

arr1 = np.array([1, 2])
arr2 = np.array([3, 4])
arr3 = np.concatenate((arr1, arr2))
print(arr3)
'''
Output:
[1 2 3 4]
concatenate可以用于两个矩阵的拼接,上面的例子可以看出默认的拼接方式是直接把列表(这里不严谨)的元素追加到另一个的后面
'''

arr1 = np.array([[1, 2], [3, 4]])
arr2 = np.array([[5, 6]])
arr3 = np.concatenate((arr1, arr2), axis=0)
arr4 = np.concatenate((arr1, arr2.T), axis=1)
print(arr3, end='\n\n')
print(arr4)
'''
Output:
[[1 2]
 [3 4]
 [5 6]]

[[1 2 5]
 [3 4 6]]
 第二个参数axis表示拼接的方向,0表示按照行的方向拼接,1表示按照列方向拼接,axis默认是0
 注意,concatenate方法只能合并同维的矩阵
'''

vstack&hstack

arr1 = np.array([[1, 2]])
arr2 = np.array([5, 6])
arr3 = np.vstack([arr1, arr2])
print(arr3)
'''
Output:
[[1 2]
 [5 6]]
 vstack可以智能的垂直方向上拼接矩阵,即使不同维度也可以拼接
'''

a = np.array([1, 2, 3])
b = np.array([2, 3, 4])
print(np.hstack([a, b]))
'''
Output:
[1 2 3 2 3 4]
和vstack同理
'''
分割
arr = np.arange(0, 10)
subarr1, subarr2, subarr3 = np.split(arr, [2, 3])
print(subarr1, subarr2, subarr3)
'''
Output:
[0 1] [2] [3 4 5 6 7 8 9]
'''
'''
split切割向时传入一个列表作为分割点,把向量切割成对应的份数
切割时是不包括切割点的。
'''

arr = np.arange(1, 10).reshape(3, -1)
arr1, arr2 = np.split(arr, [1], axis=1)
print(arr1, arr2, sep='\n\n')
arr1, arr2 = np.split(arr, [1])
print(arr1, arr2, sep='\n\n')
'''
Output:
[[1]
 [4]
 [7]]

[[2 3]
 [5 6]
 [8 9]]
 
 Output:
 [[1 2 3]]

[[4 5 6]
 [7 8 9]]
'''
'''
可以发现对于二维矩阵的切割来说,可以用axis来控制方向,0表示按第一个维度,1表示按第二个维度,其实就是按照挨个坐标轴的方向(0可以看做行,1可以看做列)
'''
同理也存在着hsplit和vsplit这种函数,这里就不记了

4.矩阵的运算

对应每个元素进行的运算
arr = np.arange(1, 10).reshape(3, -1)
print('arr * 5 = \n', arr * 5)
print('arr - 5 = \n', arr - 5)
print('sin(arr) = \n', np.sin(arr))
print('arr * arr = \n', arr * arr)
'''
Output:
arr * 5 = 
 [[ 5 10 15]
 [20 25 30]
 [35 40 45]]
arr - 5 = 
 [[-4 -3 -2]
 [-1  0  1]
 [ 2  3  4]]
sin(arr) = 
 [[ 0.84147098  0.90929743  0.14112001]
 [-0.7568025  -0.95892427 -0.2794155 ]
 [ 0.6569866   0.98935825  0.41211849]]
arr * arr = 
 [[ 1  4  9]
 [16 25 36]
 [49 64 81]]
'''
'''
可以看到,这些运算就是对arr的单独每个元素进行了运算,就连最后一个乘法也是对应的每个元素相乘,也不是真正的矩阵乘法。同理还可以进行每个元素取绝对值,取余等运算,下面再举一些
'''
arr = np.arange(1, 10).reshape(3, -1)
print('3 ** arr = \n', 3 ** arr)
print('arr ** 3 = \n', arr ** 3)
print('-arr = \n', -arr)
print('log(arr) = \n', np.log(arr))
'''
Output:
3 ** arr = 
 [[    3     9    27]
 [   81   243   729]
 [ 2187  6561 19683]]
arr ** 3 = 
 [[  1   8  27]
 [ 64 125 216]
 [343 512 729]]
-arr = 
 [[-1 -2 -3]
 [-4 -5 -6]
 [-7 -8 -9]]
log(arr) = 
 [[0.         0.69314718 1.09861229]
 [1.38629436 1.60943791 1.79175947]
 [1.94591015 2.07944154 2.19722458]]
'''
线代中的运算
A.dot(B) # 相当于矩阵中的A * B
A.T # A的转置
np.linalg.inv(A) # A的逆
np.linalg.pinv(A) # 求A的伪逆
np.linalg.solve(A, B) # 求解线性方程组,A是系数矩阵,B是解对应的向量
向量与矩阵进行运算
arr1 = np.array([1, 2])
arr2 = np.array([[1, 2],
                 [3, 4]])
print(arr1 + arr2)
print(arr1 * arr2)
'''
Output:
[[2 4]
 [4 6]]
[[1 4]
 [3 8]]
'''
'''
可以发现,这里是把向量给矩阵的每一列进行了加法运算,垂直方向也同理
'''
arr1 = np.array([1, 2])
print(np.tile(arr1, [2, 3]))
'''
Output:
[[1 2 1 2 1 2]
 [1 2 1 2 1 2]]
'''
'''
tail方法是对元素进行堆叠,第二个参数中传输的各个维度上堆叠的次数
'''
聚合运算
arr1 = np.arange(1, 26).reshape(5, -1)
print(np.sum(arr1), end='\n\n')
print(np.sum(arr1, axis=0))
'''
Output:
325

[55 60 65 70 75]
'''
'''
sum是求和操作,在没有axis参数的情况下,默认是对所有的元素求和
当有了第二个参数时,是对某一个维度进行运算,当axis=0时,就是对行进行运算也就是对每一行的对应元素进行了求和
'''
arr1 = np.arange(1, 26).reshape(5, -1)
print(np.min(arr1), end='\n\n')
print(np.min(arr1, axis=0), end='\n\n')
print(np.prod(arr1), end='\n\n')
print(np.prod(arr1, axis=0))
'''
Output:
1

[1 2 3 4 5]

2076180480

[ 22176  62832 129168 229824 375000]
'''
'''
其它的一些聚合操作,和sum大同小异其中prod是求乘积
'''
np.mean() # 求平均值
np.median() # 求中位数
np.percentile() # 求百分位
np.var() # 求方差
np.std() # 求标准差

5.索引

arg方法获取索引
arr1 = np.random.randint(25, size=(5, 5))
np.random.shuffle(arr1)
'''
random下的shuffle函数可以随机打乱一个矩阵
'''

arr1 = np.random.randint(25, size=(5, 5))
print(arr1)
print(np.argmin(arr1))
print(np.argmin(arr1, axis=0))
'''
[[22  2  3  8 10]
 [ 2 10  4 17 11]
 [ 1  2 13  3 15]
 [19 22 23 11  9]
 [ 5  3 10 16  7]]
10
[2 0 0 2 4]
'''
'''
argmin是返回最小值的索引,同样可以加axis进行不同维度上的求最小。当不加axis时默认是获取全局的最小值,返回的是一个整数,表示从上到下从左到右中最小值的位置
'''
arr1 = np.random.randint(25, size=(5, 5))
print(arr1, end='\n\n')
print(np.sort(arr1), end='\n\n')
print(np.argsort(arr1))
'''
Output:
[[22 14 18 24 23]
 [18 21  0 22  7]
 [ 9 21 13 15 18]
 [ 9 21  7  6 21]
 [20 22 19 17  1]]

[[14 18 22 23 24]
 [ 0  7 18 21 22]
 [ 9 13 15 18 21]
 [ 6  7  9 21 21]
 [ 1 17 19 20 22]]

[[1 2 0 4 3]
 [2 4 0 1 3]
 [0 2 3 4 1]
 [3 2 0 1 4]
 [4 3 2 0 1]]
'''
'''
sort方法是对一个矩阵进行某个方向上的排序,argsort则是返回排序后原元素所在的索引axis默认是1。
'''
arr1 = np.arange(10)
print(np.partition(arr1, 4))
print(np.argpartition(arr1, 4))
'''
Output:
[1 0 2 3 4 5 6 7 8 9]
[1 0 2 3 4 5 6 7 8 9]
'''
'''
partition的作用是选取一个标定点,把小于其的元素都放在前面,后面都是大于它的元素,同理argpartition返回的就是排后的索引
'''
Fancy Indexing
arr1 = np.arange(1, 10)
idx1 = np.array([2, 4, 7])
idx2 = np.array([
        [2, 1],
        [0, 1],
        [2, 2]])
print(arr1)
print(arr1[idx1])
print(arr1[idx2])
'''
Output:
[1 2 3 4 5 6 7 8 9]
[3 5 8]
[[3 2]
 [1 2]
 [3 3]]
'''
'''
当把一些列索引写入一个矩阵之中,再把矩阵当做索引去使用,那么numpy会自动的把这些索引用矩阵的元素替换掉
'''


arr1 = np.arange(1, 10).reshape(3, 3)
idx1 = np.array([2, 1, 0])
idx2 = np.array([1, 0, 0])
print(arr1, end='\n\n')
print(arr1[idx1, idx2])
'''
Output:
[[1 2 3]
 [4 5 6]
 [7 8 9]]

[8 4 1]
'''
'''
当遇到二维数组时,可以把两个一维数组当做参数传入,一个表行,一个表示列,最终会得到对应的元素
'''


arr1 = np.arange(1, 10).reshape(3, 3)
idx1 = np.array([2, 1, 0])
idx2 = np.array([1, 0, 0])
print(arr1, end='\n\n')
print(arr1[2, idx2])
print(arr1[:2, idx2])
'''
Output:
[[1 2 3]
 [4 5 6]
 [7 8 9]]

[8 7 7]
[[2 1 1]
 [5 4 4]]
'''
'''
切片与布尔值的混搭,第二个输出表示行固定为0,列为指定坐标的所有元素
第三个表示为行位前两行,列为固定列的元素,同理还可以有其他的搭配,这里就不列举了。
'''


arr1 = np.arange(1, 10).reshape(3, 3)
idx1 = np.array([True, False, True])
print(arr1, end='\n\n')
print(arr1[2, idx1])
print(arr1[:2, idx1])
'''
Output:
[[1 2 3]
 [4 5 6]
 [7 8 9]]

[7 9]
[[1 3]
 [4 6]]
'''
'''
numpy的索引也支持布尔类型的索引,对应位置是true就选择,是false就不选择
'''


arr1 = np.random.randint(10, size=(3, 3))
idx1 = arr1 < 8
idx2 = arr1 * 3 > 15
print(arr1, end='\n\n')
print(idx1, end='\n\n')
print(idx2, end='\n\n')
print(arr1[idx1])
print(arr1[idx2])
'''
Output:
[[0 4 5]
 [8 4 8]
 [4 9 8]]

[[ True  True  True]
 [False  True False]
 [ True False False]]

[[False False False]
 [ True False  True]
 [False  True  True]]

[0 4 5 4 4]
[8 8 9 8]
'''
'''
首先,可以通过比较运算符来进行比较得到一个布尔矩阵,表示哪些元素符合条件,然后再作为索引放入随机的矩阵中就可以得到想要筛选的元素,十分方便、
'''


arr1 = np.random.randint(10, size=(3, 3))
print(arr1, end='\n\n')
print(arr1 < 8)
print(np.sum(arr1 < 8))
'''
Output:
[[6 1 9]
 [1 9 2]
 [8 5 3]]

[[ True  True False]
 [ True False  True]
 [False  True  True]]
6
'''
'''
Ture转换成数字就是1而false就是0也就是以上的功能实际上就成了统计满足条件的元素的个数
'''


arr1 = np.random.randint(10, size=(3, 3))
print(arr1, end='\n\n')
print(np.any(arr1 < 3))
print(np.all(arr1 < 10))
'''
Output:
[[8 2 4]
 [4 1 0]
 [9 0 8]]

True
True
'''
'''
any方法会查看整个矩阵,如果有一个是true则返回true
all则是全为true则返回true
'''

6.matplotlib可视化

导入matplotlib.pyplot
import matplotlib.pyplot as plt
绘制折线图
x = np.linspace(1, 10, 100)
y = np.sin(x)
plt.plot(x, y)
plt.show()

Output:
在这里插入图片描述
plot方法两个参数,x和y分别对应的集合。
show方法显示图像

x = np.linspace(1, 10, 100)
y = np.sin(x)
y2 = np.cos(x)
plt.plot(x, y)
plt.plot(x, y2)
plt.show()

在这里插入图片描述
可以一次绘制多个图像


```python
x = np.linspace(1, 10, 100)
y = np.sin(x)
y2 = np.cos(x)
plt.plot(x, y, color='red', linestyle='--')
plt.plot(x, y2)
plt.show()

在这里插入图片描述
给曲线设置颜色和线条样式

x = np.linspace(1, 10, 100)
y = np.sin(x)
y2 = np.cos(x)
plt.plot(x, y, color='red', linestyle='--')
plt.plot(x, y2)
plt.xlim(2, 10)
plt.ylim(0, 2)
plt.show()

Output:
在这里插入图片描述
xlim和ylim可以用于设置坐标轴的范围

x = np.linspace(1, 10, 100)
y = np.sin(x)
y2 = np.cos(x)
plt.plot(x, y, color='red', linestyle='--', label='sin(x)')
plt.plot(x, y2, color='blue', label='cos(x)')
plt.xlabel("x value")
plt.ylabel("y value")
plt.legend()
plt.show()

Output:

在这里插入图片描述
xlabel和ylabel可以用于设置横纵坐标的含义
plot的label值可以设置函数的含义,要显示时需要调用legend方法
同时还可以加title设置标题

绘制散点图
x = np.linspace(1, 10, 100)
y = np.sin(x)
y2 = np.cos(x)
plt.scatter(x, y, color='red', label='sin(x)')
plt.xlabel("x value")
plt.ylabel("y value")
plt.legend()
plt.show()

Output:
在这里插入图片描述
除了plot变成了scatter以外,其他的都一样

x = np.random.normal(0, 1, 1000)
y = np.random.normal(0, 1, 1000)
plt.scatter(x, y, color='red', alpha=0.75)
plt.show()

Output:
在这里插入图片描述
绘制一个二维正态分布散点图,其中alpha用于调整透明度

©️2020 CSDN 皮肤主题: 深蓝海洋 设计师:CSDN官方博客 返回首页