目录
1 numpy数组使用
1.1 numpy生成数组
1.2?numpy数组属性
1.3 数组的索引和切片
1.4?numpy数组运算
1.5 随机数
2 scipy包的使用
2.1?scipy包中的模块
2.2 常数模块的使用
2.3 特殊函数模块的使用
2.4 信号处理模块
2.5 空间结构模块
3 pandas包的使用
3.1?pandas数组
3.2 数据表
3.3 查看数据
3.4 pandas读取文件
3.5 数据聚合与分组运算
4 matplotlib包的使用
4.1 二维可视化图像
4.2 一张图中的不同曲线?
?4.3 三维曲线图
4.4 其他类型曲线
4.5 三维可视化图像
4.5.1 曲面图绘制
4.5.2 曲线图和散点图绘制?
?4.6 可视化图片(女神)
Python具有强大的数据处理能力,尤以数组处理为主。numpy包是科学计算库,提供N维数组运算及各种数据分析方法;scipy包需要numpy包支持,提供积分、方程组求解等运算;matplotlib包提供数据绘图命令,所绘图像质量较高;pandas包提供提供机器学习数据格式。
1 numpy数组使用
numpy、scipy、matplotlib这3个包通常一起使用,这种组合可用于替代MATLAB软件的功能,构成一个强大的科学计算环境,有助于我们通过Python学习数据科学或机器学习。
首先安装这3种包:
pip install numpy
pip install scipy
pip install matplotlib
1.1 numpy生成数组
创建数组的方式有很多种,如可以通过将已有的元组、列表或range对象使用numpy.array()函数转换为数组的方式来生成数组。
numpy.array()函数的语法格式如下:
numpy.array(object,dtype = None,copy = True,order = None,subok = False,ndmin = 0)
#参数说明如下:
#object:表示数组或嵌套的数列;
#dtype:可选参数,表示数组元素的数据类型;
#copy:可选参数,表示对象是否需要复制;
#order:表示创建数组的样式,C为行方向,F为列方向,A为任意方向(默认);
#subok:表示默认返回一个与基类类型一致的数组;
#ndmin:表示指定生成数组的最小维度。
例1.1.1,使用numpy.array()函数将元组、列表或range对象转换成数组:
import numpy as np #导入numpy模块,并用np代替
a = (1,2,3,4,5)
b = [1,2,3,4,5]
c = [[1,2,3],[4,5,6]]
print(np.array(a)) #将元组转换成数组
print(np.array(b)) #将列表转换成数组
print(np.array(c)) #将列表转换成数组
print(np.array(range(5))) #将range对象转换成数组
运行结果如下:
[1 2 3 4 5]
[1 2 3 4 5]
[[1 2 3]
[4 5 6]]
[0 1 2 3 4]
我们还可以使用numpy.asarray()函数来创建数组。
numpy.asarray()函数的语法格式如下:
numpy.asarray(a,dtype = None,order = None)
#参数说明如下:
#a:表示数组或嵌套的数列;
#dtype:可选参数,表示数组元素的数据类型;
#order:表示创建数组的样式,C为行方向,F为列方向,A为任意方向(默认)。
例1.1.2,使用numpy.asarray()函数将元组、列表或range对象转换成数组:
import numpy as np #导入numpy模块,并用np代替
a = (1,2,3,4,5)
b = [1,2,3,4,5]
c = [[1,2,3],[4,5,6]]
print(np.asarray(a)) #将元组转换成数组
print(np.asarray(b)) #将列表转换成数组
print(np.asarray(c)) #将列表转换成数组
print(np.asarray(range(5))) #将range对象转换成数组
运行结果如下:
[1 2 3 4 5]
[1 2 3 4 5]
[[1 2 3]
[4 5 6]]
[0 1 2 3 4]
通过观察例1.1.1和例1.1.2我们发现,numpy.array()函数和numpy.asarray()函数好像没有什么区别,下面我们通过一个例子来理解两者之间的区别。
例1.1.3,numpy.array()函数和numpy.asarray()函数的不同:
import numpy as np #导入numpy模块,并用np代替
A = np.ones((3,3))
print(A)
B = np.array(A)
print(B)
C = np.asarray(A)
print(C)
A[0] = 0
print('修改后的A:\n',A)
print('修改后的B:\n',B)
print('修改后的C:\n',C)
运行结果如下:
[[1. 1. 1.]
[1. 1. 1.]
[1. 1. 1.]]
[[1. 1. 1.]
[1. 1. 1.]
[1. 1. 1.]]
[[1. 1. 1.]
[1. 1. 1.]
[1. 1. 1.]]
修改后的A:
[[0. 0. 0.]
[1. 1. 1.]
[1. 1. 1.]]
修改后的B:
[[1. 1. 1.]
[1. 1. 1.]
[1. 1. 1.]]
修改后的C:
[[0. 0. 0.]
[1. 1. 1.]
[1. 1. 1.]]
可以发现,当修改了A数组中的第一行元素后,再分别输出A、B、C数组,其中B和C数组的结果并不是完全相同的。这是因为numpy.array()函数和numpy.asarray()函数都可以将结构数据转化为ndarray,但是当数据源是ndarray时,numpy.array()函数仍然会复制出一个副本,占用新的内存,而numpy.asarray()函数不会。
还可以通过其他方式生成数组,如numpy.zeros()函数、numpy.ones()函数、numpy.identity()函数、numpy.empty()函数、numpy.linspace()函数等。
numpy.zeros()函数用于生成一个元素全为0的数组。
numpy.zeros()函数语法格式如下:
numpy.zeros(shape,dtype = float,order = 'C')
numpy.ones()函数用于生成一个元素全为1的数组。
numpy.ones()函数语法格式如下:
numpy.ones(shape,dtype = None,order = 'C')
numpy.empty()函数用于创建一个指定形状(shape)、数据类型(dtype)且未初始化的数组。
numpy.empty()函数语法格式如下:
numpy.empty(shape,dtype = float,order = 'C')
以上3种方式中,参数shape指定数组形状,即几行几列的数组;dtype指定数据类型;order指定在计算机内存中存储元素的顺序,C为行优先,F为列优先,默认为C。
numpy.identity()函数用于生成一个单位矩阵。
numpy.identity()函数语法格式如下:
numpy.identity(n,dtype = None)
其中,n为生成单位矩阵的维数。
numpy.linspace()函数用于创建一个一维数组,元素由等差数列构成。
numpy.linspace()函数语法格式如下:
numpy.linspace(start,stop,num=50,endpoint=True,retstep=False,dtype = None)
#参数说明如下:
#start:表示数列的第一个值;
#stop:表示数列的最后一个值;
#num:表示生成等步长数列的个数,默认为50;
#endpoint:表示值为True时,数列包含stop,否则不包含,默认为True;
#retstep:表示值为True时,生成数组中显示间距,否则不显示;
#dtype:表示ndarray的数据类型。
例1.1.4,对以上函数的简单应用:
import numpy #导入numpy模块
a = numpy.zeros((3,3)) #生成3行3列元素全为0的矩阵
b = numpy.ones((3,1)) #生成元素全为1的数组
c = numpy.identity(4) #生成单位矩阵
d = numpy.empty((3,3)) #生成3行3列的空矩阵,元素值随机生成
e = numpy.linspace(0,6,7) #生成一个数组,各个元素在0、6之间等分
print('numpy.zeros((3,3)):\n',a)
print('numpy.ones((3,1)):\n',b)
print('numpy.identity(4):\n',c)
print('numpy.empty((3,3)):\n',d)
print('numpy.linspace(0,6,7):\n',e)
运行结果如下:
numpy.zeros((3,3)):
[[0. 0. 0.]
[0. 0. 0.]
[0. 0. 0.]]
numpy.ones((3,1)):
[[1.]
[1.]
[1.]]
numpy.identity(4):
[[1. 0. 0. 0.]
[0. 1. 0. 0.]
[0. 0. 1. 0.]
[0. 0. 0. 1.]]
numpy.empty((3,3)):
[[0.00000000e+000 0.00000000e+000 0.00000000e+000]
[0.00000000e+000 0.00000000e+000 2.52961611e-321]
[8.34445137e-308 2.14321575e-312 9.28366228e-312]]
numpy.linspace(0,6,7):
[0. 1. 2. 3. 4. 5. 6.]
1.2?numpy数组属性
numpy数组属性及说明
属性 | 说明 | ndarray.ndim | 矩阵的秩,表维度的数量 | ndarray.shape | 数组的维度,对于矩阵,n行m列 | ndarray.size | 数组元素的总个数,相当于.shape中n*m的值 | ndarray.dtype | ndarray对象的元素类型 | ndarray.itemsize | ndarray对象中每个元素的大小,以字节为单位 | ndarray.flags | ndarray对象的内存信息 | ndarray.real | ndarray对象的实部 | ndarray.imag | ndarray对象的虚部 | ndarray.data | 包含实际数组元素的缓冲区,由于一般通过数组的索引获取元素,所以通常不需要使用这个属性 |
例1.2.1,numpy数组属性的使用:
import numpy as np #导入numpy模块,并用np代替
A = np.array([[1,2,3,4],[5,6,7,8],[9,10,11,12]])
print('矩阵的秩:',A.ndim) #求矩阵的秩
print('矩阵的行数和列数:',A.shape) #求矩阵的行数和列数
print('矩阵A:',A)
A.shape = (4,3) #ndarray.shape还可以用来调整数组的大小
print('调整后的矩阵A:',A)
print('元素的类型:',A.dtype) #求元素的类型
运行结果如下:
矩阵的秩: 2
矩阵的行数和列数: (3, 4)
矩阵A: [[ 1 2 3 4]
[ 5 6 7 8]
[ 9 10 11 12]]
调整后的矩阵A: [[ 1 2 3]
[ 4 5 6]
[ 7 8 9]
[10 11 12]]
元素的类型: int32
1.3 数组的索引和切片
通过对数组的索引和切片操作来实现对数组内容的访问和修改。对于一维数组来说,可以通过从0~n的下标进行索引,通过内置函数slice(),设置参数start、stop、step的值,切割出一个新的数组,也可以通过[start:stop:step]的方式来进行切片操作。
例1.3.1,一维数组的切片操作:
import numpy as np #导入numpy模块,并用np代替
a = np.array([1,2,3,4,5,6])
s1 = slice(1,5,2) #切片到stop结束,不包括stop处的值
print('s1:',a[s1])
b = a[1:5:1]
print('b:',b)
c = a[1::2] #省略stop
print('c:',c)
d = a[1:5] #省略step,默认为1
print('d:',d)
运行结果如下:
s1: [2 4]
b: [2 3 4 5]
c: [2 4 6]
d: [2 3 4 5]
多维数组的切片操作与一维数组的方法相同,此外,多维数组还可以通过使用省略号的方式来提取元素。
例1.3.2,多维数组的切片操作:
import numpy as np #导入numpy模块,并用np代替
A= np.array([[0,1,2,3],[4,5,6,7],[8,9,10,11]])
print('A:\n',A)
B = A[0,0:3] #对第1行进行切片和索引
print('对第1行进行切片和索引:\n',B)
C = A[::2] #对第1行和3行进行切片和索引
print('对第1行和3行进行切片和索引:\n',C)
D = A[::2,::2] #对第1行和3行进行切片和索引,在对第1行和3行中的元素分别切片和索引
print('对第1行和3行进行切片和索引,在对第1行和3行中的元素分别切片和索引:\n',D)
E = A[:,2] #对第3列元素切片索引
print('对第3列元素切片索引:\n',E)
F = A[...,2] #对第3列元素切片索引
print('对第3列元素切片索引:\n',F)
G = A[...,1:] #索引矩阵后3列元素
print('索引矩阵后3列元素:\n',G)
运行结果如下:
A:
[[ 0 1 2 3]
[ 4 5 6 7]
[ 8 9 10 11]]
对第1行进行切片和索引:
[0 1 2]
对第1行和3行进行切片和索引:
[[ 0 1 2 3]
[ 8 9 10 11]]
对第1行和3行进行切片和索引,在对第1行和3行中的元素分别切片和索引:
[[ 0 2]
[ 8 10]]
对第3列元素切片索引:
[ 2 6 10]
对第3列元素切片索引:
[ 2 6 10]
索引矩阵后3列元素:
[[ 1 2 3]
[ 5 6 7]
[ 9 10 11]]
1.4?numpy数组运算
通过numpy包可以对数组进行一些运算,或对两个数组之间的元素进行对应操作。
例1.4.1,数组运算:
import numpy as np #导入numpy模块,并用np代替
a1 = np.array([3,4,5,6,7])
b1 = np.array([[1,2,3,4,5],[1,2,3,4,5]])
print('a1每个元素乘以3:\n',a1*3) #每个元素乘以3
print('a1每个元素除以3:\n',a1/3) #每个元素除以3
print('a1每个元素的平方:\n',a1**2) #每个元素的平方
print('a1每个元素+1:\n',a1+1) #每个元素+1
print('两个数组的元素相乘:\n',a1*b1) #两个数组的元素相乘
运行结果如下:
a1每个元素乘以3:
[ 9 12 15 18 21]
a1每个元素除以3:
[1. 1.33333333 1.66666667 2. 2.33333333]
a1每个元素的平方:
[ 9 16 25 36 49]
a1每个元素+1:
[4 5 6 7 8]
两个数组的元素相乘:
[[ 3 8 15 24 35]
[ 3 8 15 24 35]]
例1.4.2,数组的特殊运算:
import numpy as np #导入numpy模块,并用np代替
a = np.array([1,2,3,4,5,6,7,8,9])
a = a.reshape(3,3) #重新构造矩阵
print('重新构造矩阵:\n',a)
print('元素和:\n',a.sum())
print('最小元素:\n',a.min())
print('最大元素:\n',a.max())
print('行求和:\n',np.sum(a,axis=1))
print('列求和:\n',np.sum(a,axis=0))
print('行最小:\n',np.min(a,axis=1))
print('行最大:\n',np.max(a,axis=1))
运行结果如下:
重新构造矩阵:
[[1 2 3]
[4 5 6]
[7 8 9]]
元素和:
45
最小元素:
1
最大元素:
9
行求和:
[ 6 15 24]
列求和:
[12 15 18]
行最小:
[1 4 7]
行最大:
[3 6 9]
补充:
import numpy as np #导入numpy模块,并用np代替
a = np.array([1,2,3,4,5,6,7,8,9])
a = a.reshape(3,3) #重新构造矩阵
print('重新构造矩阵:\n',a)
#计算标准差和方差
print('数组的标准差:',a.std())
print('数组每列的标准差:',a.std(axis=0))
print('数组每行的标准差:',a.std(axis=1))
print('数组的方差:',a.var())
print('数组每列的方差:',a.var(axis=0))
print('数组每行的方差:',a.var(axis=1))
运行结果如下:
重新构造矩阵:
[[1 2 3]
[4 5 6]
[7 8 9]]
数组的标准差: 2.581988897471611
数组每列的标准差: [2.44948974 2.44948974 2.44948974]
数组每行的标准差: [0.81649658 0.81649658 0.81649658]
数组的方差: 6.666666666666667
数组每列的方差: [6. 6. 6.]
数组每行的方差: [0.66666667 0.66666667 0.66666667]
例1.4.3,转置与点积运算:
import numpy as np #导入numpy模块,并用np代替
c = np.array([[1,2,3,4,5,6],[1,2,3,4,5,6]])
print('未转置前:\n',c)
print('转置后:\n',c.T)
运行结果如下:
未转置前:
[[1 2 3 4 5 6]
[1 2 3 4 5 6]]
转置后:
[[1 1]
[2 2]
[3 3]
[4 4]
[5 5]
[6 6]]
在例1.4.3中,通过.T操作进行了数组的转置。在numpy包中还有一种函数也可以实现数组的转置,即numpy.transpose()函数。
numpy.transpose()函数语法格式如下:
numpy.transpose(arr,axes)
#参数说明如下:
#arr:表示要转置的数组;
#axes:表示整数列表,对应维度,在默认情况下所有维度都会进行转换。
例1.4.4,numpy.transpose()函数完成转置:
import numpy as np #导入numpy模块,并用np代替
c = np.array([[1,2,3,4,5,6],[1,2,3,4,5,6]])
print('转置后:\n',np.transpose(c))
运行结果如下:
转置后:
[[1 1]
[2 2]
[3 3]
[4 4]
[5 5]
[6 6]]
例1.4.3和例1.4.4观察,两者区别是,.T操作只能进行简单的轴对换,而numpy.transpose()函数还能对高维数组进行更加复杂的操作。
例1.4.5,数组元素的访问:
import numpy as np #导入numpy模块,并用np代替
a = np.array([[1,2,3,4],[5,6,7,8],[9,10,11,12]])
print(a)
print('访问第一行元素:\n',a[0])
print('访问第一行、第二行元素:\n',a[[0,1]])
print('访问第一行第二列元素:\n',a[0][1])
运行结果如下:
[[ 1 2 3 4]
[ 5 6 7 8]
[ 9 10 11 12]]
访问第一行元素:
[1 2 3 4]
访问第一行、第二行元素:
[[1 2 3 4]
[5 6 7 8]]
访问第一行第二列元素:
2
例1.4.6,数组元素函数运算:
import numpy as np #导入numpy模块,并用np代替
a = np.array([[3,7,9,11],[4,6,8,10]])
print('a/2:\n',a/2)
print('向下取整:\n',np.floor(a/2))
print('向上取整:\n',np.ceil(a/2))
print('四舍五入:\n',np.round(a/2))
运行结果如下:
a/2:
[[1.5 3.5 4.5 5.5]
[2. 3. 4. 5. ]]
向下取整:
[[1. 3. 4. 5.]
[2. 3. 4. 5.]]
向上取整:
[[2. 4. 5. 6.]
[2. 3. 4. 5.]]
四舍五入:
[[2. 4. 4. 6.]
[2. 3. 4. 5.]]
1.5 随机数
随机数是机器学习中经常使用的内容。其中设置随机数种子,可以使用np.random.seed()函数,它可以保证在使用随机函数生成随机数时,随机数是可重复出现的;生成服从正态分布的随机数可以使用np.random.randn()函数;生成0~n整数的随机排序可以使用np.random.permutation()函数;生成服从均匀分布的随机数可以使用np.random.randn()函数;在指定范围生成随机数可以使用np.random.randint()函数。
对随机数种子的理解可以参考该博主的博文:
np.random.seed()随机数种子_程序员_Iverson的博客-CSDN博客
import numpy as np #导入numpy模块,并用np代替
#设置随机数种子
np.random.seed(11) #该参数值确定了生成随机数的顺序
#1、生成正态分布的随机数矩阵
a = np.random.randn(3,3)
print('生成正态分布的随机数矩阵:\n',a)
#2、将0~10之间的数进行随机排序
#设置随机数种子
np.random.seed(11) #该参数值确定了生成随机数的顺序
b = np.random.permutation(10)
print('将0~10之间的数进行随机排序:\n',b)
#3、生成均匀分布的随机数矩阵
np.random.seed(11)
c = np.random.rand(2,3)
print('生成均匀分布的随机数矩阵:\n',c)
#4、在范围内生成随机数整数
np.random.seed(11)
d = np.random.randint(low=2,high=10,size=15)
print('在范围内生成随机数整数:\n',d)
运行结果如下:
生成正态分布的随机数矩阵:
[[ 1.74945474 -0.286073 -0.48456513]
[-2.65331856 -0.00828463 -0.31963136]
[-0.53662936 0.31540267 0.42105072]]
将0~10之间的数进行随机排序:
[7 8 2 6 4 5 1 3 0 9]
生成均匀分布的随机数矩阵:
[[0.18026969 0.01947524 0.46321853]
[0.72493393 0.4202036 0.4854271 ]]
在范围内生成随机数整数:
[3 9 2 5 3 9 7 6 3 9 4 2 7 6 2]
2 scipy包的使用
scipy是一个用于数学、科学和工程领域的常用软件包,可以用来进行图像处理、积分、插值、傅里叶变化、常微分方程等问题的求解。scipy包是基于numpy包开发的,能够有效地计算numpy数组,使numpy包和scipy包协同工作。
2.1?scipy包中的模块
Scipy包中各模块
模块 | 说明 | scipy.cluster | 聚类模块,包括两类聚类方法,即矢量量化和层次聚类。 | scipy.constants | 常数模块,包含了许多数学常数和物理常数,如光速、圆周率、大气压强、黄金分割率等。 | scipy.special | 特殊函数模块,可以直接调用各类函数功能。 | scipy.integrate | 积分模块,可以求多重积分、高斯积分、解微分方程。 | scipy.odr | 正交距离回归模块,可以执行显式或隐式正交距离回归拟合,也可以执行普通最小二乘法。 | scipy.optimize | 优化模块,包含各类优化算法,如求有/无约束的多元标量函数最小值算法、最小二乘法、求有/无约束的单变量函数最小值算法等。 | scipy.interpolation | 插值模块,提供各种一维、二维、N维插值算法,包括B样条插值、径向基函数插值等。 | scipy.fftpack | 快速傅里叶变换模块,可以进行快速傅里叶变换、离散余弦变换、离散正弦变换。 | scipy.signal | 信号处理模块,包括样条插值、卷积、差分等滤波方法,还有有限脉冲响应、无线脉冲响应、中值、排序、维纳、希尔伯特等滤波器设计,以及各种谱分析方法。 | scipy.linalg | 线代模块,提供各种线性代数中的常规操作。 | scipy.sparse | 稀疏矩阵模块,提供大型稀疏矩阵计算中的各种算法。 | scipy.spatial | 空间结构模块,提供一些空间相关的数据结构和算法,如Delaunay三角剖分、共面点、凸包、维诺图、kd树等。 | scipy.stats | 统计模块,提供一些统计学上常用的函数。 | scipy.ndimage | 多维图像处理模块,提供一些多维图像处理上的常用算法。 | scipy.io | IO模块,提供与其他文件的接口,如MATLAB文件、IDL文件、WAV(音频)文件、ARFF文件。 |
2.2 常数模块的使用
例2.2.1,常数模块的使用:
from scipy import constants as C
print('大气压强:',C.atmosphere)
print('圆周率:',C.pi)
print('黄金分割率:',C.golden)
print('光速:',C.c)
运行结果如下:
大气压强: 101325.0
圆周率: 3.141592653589793
黄金分割率: 1.618033988749895
光速: 299792458.0
2.3 特殊函数模块的使用
特殊函数模块中包含了一些常用的杂项函数,包括立方根函数、指数函数、β函数、γ函数等。
例2.3.1,特殊函数模块的使用:
from scipy import special as S
print('求立方根:',S.cbrt(8))
print('10**3:',S.exp10(3))
print('正弦函数,参数为角度:',S.sindg(90))
print('四舍五入函数:',S.round(2.1))
print('从5中任选3个的组合数:',S.comb(5,3))
print('从5中任选3个的排列数:',S.perm(5,3))
print('γ函数:',S.gamma(4))
print('β函数:',S.beta(10,200))
print('sinc函数:',S.sinc(0))
运行结果如下:
求立方根: 2.0
10**3: 1000.0
正弦函数,参数为角度: 1.0
四舍五入函数: 2.0
从5中任选3个的组合数: 10.0
从5中任选3个的排列数: 60.0
γ函数: 6.0
β函数: 2.839607777781333e-18
sinc函数: 1.0
2.4 信号处理模块
信号处理模块中包括卷积(convolution)、B样条(B-splines)、滤波设计器(filter design)、连续时间线性系统(continuous-time linear systems)、离散时间线性系统(discrete-time linear systems)、线性时不变表示(linear time invarian representations)、小波分析(wavelets)、峰值点(peak finding)、谱分析(spectral analysis)功能。
卷积运算是信号处理中的基本运算,在时域分析中,系统的输出一般可以表示成输入信号与系统函数的卷积运算。
Python中一维卷积运算函数的语法格式如下:
signal.convolve(in1,in2,mode='full',method='auto')
#参数说明如下:
#in1:第一信号
#in2:第二信号
#mode:输出模式,mode='full'时,输出为满离散线性卷积,mode='valid'时,输出只包含那些不依赖于零填充的元素,mode='same'时,输出与被卷积矩阵大小相同的矩阵
#method:卷积方式,method='fft',采用快速傅里叶法,method='direct',采用定义法,method='auto',自动选择fft或direct进行卷积
例2.4.1,一维卷积滤波:
from scipy import signal
import numpy as np
import matplotlib.pyplot as plt
t = np.arange(-1,1,0.1)
n = t.size
in1 = 1-t**2
in2 = np.zeros(n)
for i in range(n):
in2[i] = 1-abs(round(t[i]))
filtered = signal.convolve(in1,in2,mode='same')/sum(in2)
plt.plot(filtered,'o-',)
plt.plot(in1,'*-',)
plt.plot(in2,'v-',)
plt.show()
运行结果如下:
?例2.4.2,二维图片卷积:
import PIL #PIL为旧版本,安装pillow模块即可代替PIL
from PIL import Image #导入Image图像处理模块
from scipy import signal,misc
import matplotlib.pyplot as plt
import numpy as np
import pylab #matplotlib中包含的模块
im = PIL.Image.open('E:\CSDN\python\yun_20.jpg')
# im = plt.imread('E:\CSDN\python\yun_20.jpg') #这两句很有用
# plt.imsave('res.jpg',res)
#im.show() #注释1
w = np.zeros((50,50))
w[0][0] = 1
w[49][20] = 1.0
img = im.convert('L')
#img.show() #注释2
image_new = signal.fftconvolve(img,w) #与convolve用法类似,但只能使用傅里叶卷积
plt.figure()
plt.imshow(image_new) #这两句要结合在一起使用才能显示处理后数据的图片
#pylab.show()
plt.show() #注释3,同pylab.show()。注意:注释1、2、3最好在一次运行程序中注释掉其中的两个,例如,将注释1和2注释,保留3
运行结果如下:(处理时间可能较长,请耐心等待)
?处理前的照片
第二个注释(注释2处)的照片?
?
?处理后的照片
还可以通过使用scipy包中的signal模块和ndimage模块对图片进行滤波处理。滤波有很多种,如平滑、锐化、边缘增强等。对图像进行这些滤波处理,是为了突出图像的一些特征,弱化或删除图像的另一些特征。
例2.4.3,高斯滤波、模糊、锐化:
#高斯滤波和锐化操作
import PIL #PIL为旧版本,安装pillow模块即可代替PIL
from PIL import Image #导入Image图像处理模块
from scipy import signal,misc
import matplotlib.pyplot as plt
import numpy as np
import pylab #matplotlib中包含的模块
from scipy import ndimage
im = PIL.Image.open('E:\CSDN\python\yun_20.jpg')
#im.show() #注释1
#高斯滤波,模糊
blurred_plane = ndimage.gaussian_filter(im,sigma=3)
plt.figure()
plt.imshow(blurred_plane) #这两句要结合在一起使用才能显示处理后数据的图片
plt.show() #注释2
#锐化操作
blurred_plane2 = ndimage.gaussian_filter(im,sigma=0.2)
sharp_plane = blurred_plane2+5*(blurred_plane2-blurred_plane)
plt.figure()
plt.imshow(sharp_plane) #这两句要结合在一起使用才能显示处理后数据的图片
plt.show() #注释3,注意:注释1、2、3最好在一次运行程序中注释掉其中的两个,例如,将注释1和2注释,保留3
运行结果如下:(处理时间可能较长,请耐心等待)
?处理前的照片
高斯滤波和模糊处理后的图片?
锐化处理后的图片?
还可以通过边缘检测技术对图像进行边缘提取。边缘检测技术是一种用于查找图像内物体边界的图像处理技术,是图像分割和机器视觉中的基本问题常用的边缘检测算法包括Sobel算子、Canny算子、Prewitt、Roberts和Fuzzy Logic methods。下面例2.4.4我们将使用sobel()函数来检测图形边缘,sobel()函数按轴对图像数组进行操作,得到两个矩阵,然后通过hypot()函数将两矩阵合并输出。
例2.4.4,边缘检测技术:
#边缘检测技术
import scipy.ndimage as nd
import numpy as np
import matplotlib.pyplot as plt
#生成测试图像
im = np.zeros((128,128))
im[32:-32,32:-32] = 2
im = nd.gaussian_filter(im,4)
#处理前图像显示
plt.imshow(im) #这两句要结合在一起使用才能显示处理后数据的图片
plt.show()
#进行边缘检测处理
sx = nd.sobel(im,axis=0,mode='constant')
sy = nd.sobel(im,axis=1,mode='constant')
#将矩阵sx,sy合并
sob = np.hypot(sx,sy)
#处理后图像显示
plt.imshow(sob) #这两句要结合在一起使用才能显示处理后数据的图片
plt.show() #在显示处理后的图片时最好把处理前的图像给注释掉
运行结果如下:
处理前图像显示?
边缘检测处理后的图像?
2.5 空间结构模块
例2.5.1,计算两个点之间的欧氏距离:
#计算两个点之间的欧氏距离
import numpy as np
from scipy.spatial.distance import pdist,squareform,cdist
x1 = np.array([[1,3]])
x2 = np.array([[4,9]])
#计算两个点之间的欧氏距离
distance = cdist(x1,x2,'euclidean')
print('两个点之间的欧氏距离:\n',distance)
X = np.array([[1,2],[2,7],[3,5]])
#计算与每行点(包括自身)之间的欧氏距离
distance_X = squareform(pdist(X,'euclidean'))
print('每行点(包括自身)之间的欧氏距离:\n',distance_X)
运行结果如下:
两个点之间的欧氏距离:
[[6.70820393]]
每行点(包括自身)之间的欧氏距离:
[[0. 5.09901951 3.60555128]
[5.09901951 0. 2.23606798]
[3.60555128 2.23606798 0. ]]
3 pandas包的使用
pandas包是基于numpy包开发的数据分析库,是机器学习必须要用到的拓展库,简单介绍使用方法。
pandas包主要包含3种数据结构。
(1)Series为带标签的一维数组,是一个基于numpy包的ndarray结构,类似于Python语言中的List,与其不同的是,Series中存储数据类型相同的数据,以便提高运算效率。
(2)DataFrame为二维表格,带标签,包含一组有序的列,但每一列的数据类型可以不同,可以看作由多个Series组成的字典,在DataFrame中称为columns。
(3)Panel为三维数组,带标签。
3.1?pandas数组
Series类型的数据就像“竖着的”列表,列表中每个数据都对应一个索引值。导入pandas包后通过
pandas.Series(data=None,index=None,dtype=None,name=None,copy=False,fastpath=False)函数来生成一个一维数组。其中,data可以是数组、可迭代对象、字典或标量值;index用于传入自定义索引,否则传入默认索引[0,1,2,...,n],个数与data长度相同。
例3.1.1,生成一维数组:
(1)通过列表构建Series:
import pandas as pd
import numpy as np
a = pd.Series([1,2,3,np.nan]) #通过列表构建Series
print(a)
运行结果如下:
0 1.0
1 2.0
2 3.0
3 NaN
dtype: float64
(2)自定义索引:
import pandas as pd
import numpy as np
b = pd.Series([1,2,3,np.nan],index=['A','B','C','D']) #自定义索引
print(b)
运行结果如下:
A 1.0
B 2.0
C 3.0
D NaN
dtype: float64
(3)通过numpy.array构建Series并自定义索引:
import pandas as pd
import numpy as np
x = np.array([1,2,3,4])
c = pd.Series(x,index=['A','B','C','D']) #通过numpy.array构建Series并自定义索引
print(c)
运行结果如下:
A 1
B 2
C 3
D 4
dtype: int32
(4)通过字典构建Series:
import pandas as pd
d = {'A':1,'B':2,'C':3,'D':4}
e = pd.Series(d) #通过字典构建Series
print(e)
运行结果如下:
A 1
B 2
C 3
D 4
dtype: int64
例3.1.2,利用Series的方法获取索引或值:
import pandas as pd
import numpy as np
b = pd.Series([1,2,3,np.nan],index=['A','B','C','D']) #自定义索引
print('获取b的值:\n',b.values)
print('获取b的类型:\n',type(b.values)) #可以看到,虽然传入的是列表结构,输出的仍然是ndarray结构
print('获取b的索引:\n',b.index)
print('通过索引获取b的值:\n',b['B'])
print('通过位置获取b的值:\n',b[0:2])
运行结果如下:
获取b的值:
[ 1. 2. 3. nan]
获取b的类型:
<class 'numpy.ndarray'>
获取b的索引:
Index(['A', 'B', 'C', 'D'], dtype='object')
通过索引获取b的值:
2.0
通过位置获取b的值:
A 1.0
B 2.0
dtype: float64
例3.1.3,生成二维数组:
(1)range()对象
import pandas as pd
date1 = pd.date_range(start='20220614', end='20220714',freq='D')
print(date1)
运行结果如下:
DatetimeIndex(['2022-06-14', '2022-06-15', '2022-06-16', '2022-06-17',
'2022-06-18', '2022-06-19', '2022-06-20', '2022-06-21',
'2022-06-22', '2022-06-23', '2022-06-24', '2022-06-25',
'2022-06-26', '2022-06-27', '2022-06-28', '2022-06-29',
'2022-06-30', '2022-07-01', '2022-07-02', '2022-07-03',
'2022-07-04', '2022-07-05', '2022-07-06', '2022-07-07',
'2022-07-08', '2022-07-09', '2022-07-10', '2022-07-11',
'2022-07-12', '2022-07-13', '2022-07-14'],
dtype='datetime64[ns]', freq='D')
(2)字典
import pandas as pd
data = {'Name':['A','B','C'],'Location':['a','b','c'],'Distance':[1,2,3]}
data_pandas = pd.DataFrame(data)
print(data_pandas)
运行结果如下:
Name Location Distance
0 A a 1
1 B b 2
2 C c 3
(3)数组
import pandas as pd
import numpy as np
a = np.array([1,2,3])
b = np.array([0,1,2,3])
c = pd.DataFrame([a,b])
print(c)
运行结果如下:
0 1 2 3
0 1 2 3 NaN
1 0 1 2 3.0
NaN表示,若生成的一维数组维数不同时,对应索引的值不存在,则为NaN。
(4)
import pandas as pd
import numpy as np
a = pd.Series(np.array([1,2,3,4]))
b = pd.Series(np.array([5,6,7,8]))
data = pd.DataFrame([a,b])
print(data)
data1 = pd.DataFrame({'A':a,'B':b})
print(data1)
运行结果如下:
0 1 2 3
0 1 2 3 4
1 5 6 7 8
A B
0 1 5
1 2 6
2 3 7
3 4 8
使用DataFrame还可以生成包含不同数据类型的数组。
例3.1.4,使用DataFrame生成包含不同数据类型的数组:
import pandas as pd
import numpy as np
a = pd.DataFrame({'Name':['apple','banana','orange'],'Number':np.array([2,3,1],dtype = 'int32'),
'Date':pd.date_range(start='20220614',end='20220616',freq='D')})
print(a)
运行结果如下:
Name Number Date
0 apple 2 2022-06-14
1 banana 3 2022-06-15
2 orange 1 2022-06-16
3.2 数据表
数据表示pandas库提供的一种二维数据结构,数据按行和列的表格方式排列,是数据分析经常使用的数据展示方式。数据表的生成通常使用pd.DataFrame(data,index,columns,...)方式。其中,data可以使用字典、数组等内容,index用于指定数据表的索引,columns用于指定数据表的列名。
使用字典生成数据时,字典的键将会作为数据表格的列名,值将会作为对应列的内容。同时可以使用df1["列名"]的形式为数据表格df1添加新的列,或获取对应列的内容。df1.columns属性可以获取输出数据表格的列名。
import pandas as pd
#1、将字典生成数据表
data = {"name":["Anan","Adams","Tom","Jara","Aql"],"age":[20,15,10,18,25],"sex":["F","M","F","F","M"]}
df1 = pd.DataFrame(data=data)
print('将字典生成数据表:\n',df1)
#2、为数据表添加新的变量
df1["high"] =[175,170,165,180,178]
print('为数据表添加新的变量:\n',df1)
#3、获取数据表的列名
print('获取数据表的列名:\n',df1.columns)
#4、通过列名获取数据表中的数据
print('通过列名获取数据表中的数据:\n',df1[["name","age"]])
运行结果如下:
将字典生成数据表:
name age sex
0 Anan 20 F
1 Adams 15 M
2 Tom 10 F
3 Jara 18 F
4 Aql 25 M
为数据表添加新的变量:
name age sex high
0 Anan 20 F 175
1 Adams 15 M 170
2 Tom 10 F 165
3 Jara 18 F 180
4 Aql 25 M 178
获取数据表的列名:
Index(['name', 'age', 'sex', 'high'], dtype='object')
通过列名获取数据表中的数据:
name age
0 Anan 20
1 Adams 15
2 Tom 10
3 Jara 18
4 Aql 25
针对数据表格df可以使用df.loc获取指定的数据,使用方式为df.loc[index_name,col_name],选择指定位置的数据:
import pandas as pd
#将字典生成数据表
data = {"name":["Anan","Adams","Tom","Jara","Aql"],"age":[20,15,10,18,25],"sex":["F","M","F","F","M"]}
df1 = pd.DataFrame(data=data)
df1["high"] =[175,170,165,180,178]
print('将字典生成数据表:\n',df1)
#输出某一行
print('输出某一行:\n',df1.loc[2])
#输出多行
print('输出多行:\n',df1.loc[1:3]) #包括第一行和第三行
#输出指定的行和列
print('输出指定的行和列:\n',df1.loc[1:3,["name","age"]]) #包括第一行和第三行
#输出性别为F的行和列
print('输出性别为F的行和列:\n',df1.loc[df1.sex=="F",["name","sex"]])
运行结果如下:
将字典生成数据表:
name age sex high
0 Anan 20 F 175
1 Adams 15 M 170
2 Tom 10 F 165
3 Jara 18 F 180
4 Aql 25 M 178
输出某一行:
name Tom
age 10
sex F
high 165
Name: 2, dtype: object
输出多行:
name age sex high
1 Adams 15 M 170
2 Tom 10 F 165
3 Jara 18 F 180
输出指定的行和列:
name age
1 Adams 15
2 Tom 10
3 Jara 18
输出性别为F的行和列:
name sex
0 Anan F
2 Tom F
3 Jara F
数据表格的df.iloc方法是基于位置的索引来获取对应的内容,相关使用方法如下:
import pandas as pd
import numpy as np #导入numpy模块,并用np代替
#将字典生成数据表
data = {"name":["Anan","Adams","Tom","Jara","Aql"],"age":[20,15,10,18,25],"sex":["F","M","F","F","M"]}
df1 = pd.DataFrame(data=data)
df1["high"] =[175,170,165,180,178]
print('将字典生成数据表:\n',df1)
#1、获取指定的行
print('1、获取指定的行:\n',df1.iloc[0:2]) #不包括第二行
#2、获取指定的列
print('2、获取指定的列:\n',df1.iloc[:,0:2]) #不包括第二列
#3、获取指定位置的数据
print('3、获取指定位置的数据:\n',df1.iloc[0:2,1:4])
#4、根据条件索引获取数据,需要将索引转化为列表或数组
print('4、根据条件索引获取数据,需要将索引转化为列表:\n',df1.iloc[list(df1.sex=="F"),0:3])
print('4、根据条件索引获取数据,需要将索引转化为数组:\n',df1.iloc[np.array(df1.sex=="F"),0:3])
#5、为数据列表内的内容重新赋值
df1.high=[170,175,177,178,180]
print('5、为数据列表内的内容重新赋值:\n',df1)
#6、选择指定的区域并重新赋值
df1.iloc[0:1,0:2]=["Apple",22]
print('6、选择指定的区域并重新赋值:\n',df1)
?运行结果如下:
将字典生成数据表:
name age sex high
0 Anan 20 F 175
1 Adams 15 M 170
2 Tom 10 F 165
3 Jara 18 F 180
4 Aql 25 M 178
1、获取指定的行:
name age sex high
0 Anan 20 F 175
1 Adams 15 M 170
2、获取指定的列:
name age
0 Anan 20
1 Adams 15
2 Tom 10
3 Jara 18
4 Aql 25
3、获取指定位置的数据:
age sex high
0 20 F 175
1 15 M 170
4、根据条件索引获取数据,需要将索引转化为列表:
name age sex
0 Anan 20 F
2 Tom 10 F
3 Jara 18 F
4、根据条件索引获取数据,需要将索引转化为数组:
name age sex
0 Anan 20 F
2 Tom 10 F
3 Jara 18 F
5、为数据列表内的内容重新赋值:
name age sex high
0 Anan 20 F 170
1 Adams 15 M 175
2 Tom 10 F 177
3 Jara 18 F 178
4 Aql 25 M 180
6、选择指定的区域并重新赋值:
name age sex high
0 Apple 22 F 170
1 Adams 15 M 175
2 Tom 10 F 177
3 Jara 18 F 178
4 Aql 25 M 180
3.3 查看数据
通过head()函数和tail()函数可以查看DataFrame的头部数据和尾部数据,默认显示5行数据,也可以指定显示数据的量,还可以使用describe()函数快速查看数据的统计摘要。
例3.3.1,查看DataFrame中的数据
import pandas as pd
import numpy as np
a = pd.DataFrame(np.random.rand(7,6),columns=['A','B','C','D','E','F'])
print('数组a:\n',a)
print('默认显示前5行数据:\n',a.head()) #默认显示前5行数据
print('显示后2行数据:\n',a.tail(2)) #显示后2行数据
print('显示索引:\n',a.index)
print('显示列名:\n',a.columns)
print('统计摘要:\n',a.describe())
运行结果如下:
数组a:
A B C D E F
0 0.924391 0.504117 0.327886 0.430448 0.679411 0.919687
1 0.835289 0.419598 0.760196 0.550578 0.911504 0.258997
2 0.236071 0.415990 0.099253 0.884899 0.979043 0.150356
3 0.862990 0.050367 0.446068 0.996250 0.352627 0.044218
4 0.205520 0.114857 0.720412 0.044878 0.455462 0.316059
5 0.505912 0.302916 0.775930 0.503188 0.920199 0.921045
6 0.047646 0.948672 0.401486 0.642486 0.159077 0.948502
默认显示前5行数据:
A B C D E F
0 0.924391 0.504117 0.327886 0.430448 0.679411 0.919687
1 0.835289 0.419598 0.760196 0.550578 0.911504 0.258997
2 0.236071 0.415990 0.099253 0.884899 0.979043 0.150356
3 0.862990 0.050367 0.446068 0.996250 0.352627 0.044218
4 0.205520 0.114857 0.720412 0.044878 0.455462 0.316059
显示后2行数据:
A B C D E F
5 0.505912 0.302916 0.775930 0.503188 0.920199 0.921045
6 0.047646 0.948672 0.401486 0.642486 0.159077 0.948502
显示索引:
RangeIndex(start=0, stop=7, step=1)
显示列名:
Index(['A', 'B', 'C', 'D', 'E', 'F'], dtype='object')
统计摘要:
A B C D E F
count 7.000000 7.000000 7.000000 7.000000 7.000000 7.000000
mean 0.516831 0.393788 0.504462 0.578961 0.636760 0.508409
std 0.361327 0.295867 0.256618 0.312413 0.320567 0.403315
min 0.047646 0.050367 0.099253 0.044878 0.159077 0.044218
25% 0.220795 0.208886 0.364686 0.466818 0.404044 0.204676
50% 0.505912 0.415990 0.446068 0.550578 0.679411 0.316059
75% 0.849140 0.461857 0.740304 0.763692 0.915852 0.920366
max 0.924391 0.948672 0.775930 0.996250 0.979043 0.948502
3.4 pandas读取文件
pandas包内置的大量函数能够处理日常所用的各类文件,包括TXT文件、Excel文件、CSV文件、JSON文件。
(1)使用read_table()函数读取TXT文件。注意,在读取所有类型的文件时,必须保证文件内容是格式化的,否则会出现读取错误的情况。
首先,创建一个TXT类型的文件grade.txt,文件内容如下:
Name,Chinese,Math,English
A,70,82,97
B,89,80,94
C,86,88,79
C,86,88,79
然后,进行数据的读取。在read_table()函数函数中,通过参数filename指定文件名,参数sep指定每行数据的分隔符,默认分隔符为sep='\t',这里需要设置为sep=',',读取的数据类型为DataFrame,代码如下:
import pandas as pd
grade = pd.read_table('grade.txt',sep=',')
print(grade)
#获取grade.txt文件中数据的函数和列数
print("行数:\n",grade.shape[0])
print("列数:\n",grade.columns.size)
运行结果如下:
Name Chinese Math English
0 A 70 82 97
1 B 89 80 94
2 C 86 88 79
3 C 86 88 79
行数:
4
列数:
4
在前面的数据输出可以观察到,读取数据的第三行和第四行为重复数据,可以通过Name来对数据进行去重。
import pandas as pd
grade = pd.read_table('grade.txt',sep=',')
u_grade = grade.drop_duplicates(['Name'])
print(u_grade)
运行结果如下:
Name Chinese Math English
0 A 70 82 97
1 B 89 80 94
2 C 86 88 79
还可以对数据进行一些简单的操作。例如,计算每一门课程的平均分。
import pandas as pd
grade = pd.read_table('grade.txt',sep=',')
u_grade = grade.drop_duplicates(['Name'])
# print(u_grade)
row = grade.shape[0]
aver_Chinese = u_grade['Chinese'].sum()/(row-1)
aver_Math = u_grade['Math'].sum()/(row-1)
aver_English = u_grade['English'].sum()/(row-1)
print('语文平均分:',aver_Chinese)
print('数学平均分:',aver_Math)
print('英语平均分:',aver_English)
运行结果如下:
语文平均分: 81.66666666666667
数学平均分: 83.33333333333333
英语平均分: 90.0
(2)对于CSV文件的读取,可以使用read_csv()函数,使用方法与read_table()函数类似,只是read_csv()函数的参数sep的默认分隔符是','。也可以使用read_csv()函数来读取TXT类型的文件。需要注意的是,在用read_csv()函数读取文件时,若文件名为中文,则可能会出现错误,可以用以下方法来解决。
首先,创建一个CSV类型的文件成绩.csv,文件内容如下:
Name,Chinese,Math,English
A,70,82,97
B,89,80,94
C,86,88,79
C,86,88,79
然后,进行数据的读取。
import pandas as pd
f = open('成绩.csv')
df = pd.read_csv(f)
print(df)
运行结果如下:
Name Chinese Math English
0 A 70 82 97
1 B 89 80 94
2 C 86 88 79
3 C 86 88 79
(3)对于JSON文件,可以使用read_json()函数进行读取。若读取时出现中文乱码,将参数encoding设置为'utf-8'即可,返回类型也是DataFrame。
首先,创建grade.json文件,内容如下:
{
"Chinese": {
"A": 70,
"B": 89,
"C": 86
},
"Math": {
"A": 82,
"B": 80,
"C": 88
},
"English": {
"A": 97,
"B": 94,
"C": 79
}
}
然后,进行数据的读取。
import pandas as pd
grade_json = pd.read_json('grade.json')
print(grade_json)
运行结果如下:
Chinese Math English
A 70 82 97
B 89 80 94
C 86 88 79
(4)对于EXCEL文件,可以通过read_excel()函数进行读取。在读取EXCEL文件时,可能会出现“No module named openpyxl”的错误,可以通过“pip install openpyxl”等命令下载openpyxl模块解决此类问题。
首先,创建grade.xlsx文件,内容如下:
?然后,进行数据的读取。
import pandas as pd
grade_excel = pd.read_excel('grade.xlsx')
print(grade_excel)
注意,若没有安装‘openpyxl’模块的话是不能读取的。
运行结果如下:
Name Chinese Math English
0 A 70 82 97
1 B 89 80 94
2 C 86 88 79
3.5 数据聚合与分组运算
pandas库提供了强大的数据聚合和分组运算能力,如可以通过apply方法,将指定的函数作用于数据和行和列,groupby方法可以对数据进行分组统计,这些功能对数据表的变换、分析和计算都非常有用。下面使用鸢尾花数据集介绍如何使用apply方法将函数应用于数据计算。
Iris.csv演示文件获取:
链接:https://pan.baidu.com/s/1gM8fRcnRHmTjCt3001Hfrg? 提取码:whj6
import pandas as pd
import numpy as np
#读取用于演示的数据
Iris = pd.read_csv("E:/PYTHON/Iris.csv")
print(Iris)
#使用apply方法将函数应用于数据
#计算每列的平均值
print('计算每列的平均值:\n',Iris.iloc[:,1:5].apply(func=np.mean,axis=0))
#计算每列的最小值和最大值
min_max = Iris.iloc[:,1:5].apply(func=(np.min,np.max),axis=0)
print('计算每列的最小值和最大值:\n',min_max)
#计算每列的样本数量
print('计算每列的样本数量:\n',Iris.iloc[:,1:5].apply(func=np.size,axis=0))
#根据行进行计算
des = Iris.iloc[:,1:5].apply(func=(np.min,np.max,np.mean,np.std,np.var),axis=1)
print('根据行进行计算:\n',des)
运行结果如下:
Id sepal length (cm) ... petal width (cm) Species
0 1 5.1 ... 0.2 setosa
1 2 4.9 ... 0.2 setosa
2 3 4.7 ... 0.2 setosa
3 4 4.6 ... 0.2 setosa
4 5 5.0 ... 0.2 setosa
[5 rows x 6 columns]
计算每列的平均值:
sepal length (cm) 4.86
sepal width (cm) 3.28
petal length (cm) 1.40
petal width (cm) 0.20
dtype: float64
计算每列的最小值和最大值:
sepal length (cm) ... petal width (cm)
amin 4.6 ... 0.2
amax 5.1 ... 0.2
[2 rows x 4 columns]
计算每列的样本数量:
sepal length (cm) 5
sepal width (cm) 5
petal length (cm) 5
petal width (cm) 5
dtype: int64
根据行进行计算:
amin amax mean std var
0 0.2 5.1 2.550 2.179449 4.750000
1 0.2 4.9 2.375 2.036950 4.149167
2 0.2 4.7 2.350 1.997498 3.990000
3 0.2 4.6 2.350 1.912241 3.656667
4 0.2 5.0 2.550 2.156386 4.650000
数据表的groupby方法则可进行分组统计,其在应用上比apply方法更加广泛,如根据数据的不同类型,计算数据的一些统计性质,获得数据透视表。相关使用示例如下:
#利用groupby进行分组统计
import pandas as pd
#读取用于演示的数据
Iris = pd.read_csv("E:/PYTHON/Iris.csv")
print(Iris)
#分组计算均值
res = Iris.drop("Id",axis=1).groupby(by="Species").mean()
print('分组计算均值:\n',res)
#分组计算偏度
res = Iris.drop("Id",axis=1).groupby(by="Species").skew()
print('分组计算偏度:\n',res)
运行结果如下:
Id sepal length (cm) ... petal width (cm) Species
0 1 5.1 ... 0.2 setosa
1 2 4.9 ... 0.2 setosa
2 3 4.7 ... 0.2 setosa
3 4 4.6 ... 0.2 setosa
4 5 5.0 ... 0.2 setosa
[5 rows x 6 columns]
分组计算均值:
sepal length (cm) ... petal width (cm)
Species ...
setosa 4.86 ... 0.2
[1 rows x 4 columns]
分组计算偏度:
sepal length (cm) ... petal width (cm)
Species ...
setosa -0.235514 ... 0.0
[1 rows x 4 columns]
4 matplotlib包的使用
matplotlib是Python语言的数据化可视包,可以绘制多种高质量图形。该包依赖于numpy包和tkinter包。常利用matplotlib包中的plot()函数进行各种点线绘制,该函数在matplotlib.pyplot中。
plot()函数的语法格式如下:
plot(x,y,'xxx',label,linewidth)
参数说明如下:
x: 位置参数, 点的横坐标,可迭代对象;
y: 位置参数, 点的横坐标,可迭代对象;
'xxx': 位置参数,点和线的样式。又分为3种属性,分别为颜色(color)、点型(marker)、线型(linestyle),可结合使用,具体形式为'[color][marker][linestyle]',数据类型为字符串。若属性用的是全名,则不能用'[color][marker][linestyle]'参数来组合赋值,应该用关键字参数对单个属性赋值。
1)颜色属性:'g':绿色,'b':蓝色,'c':蓝绿色,'m':洋红色,'r':红色,'y':黄色,'m':品红色,'k':黑色,'w':白色。也可以对关键字参数赋十六进制的RGB字符串,如color='#900302'。
2)点型属性:'.':点,'v':实心倒三角,'o':实心圆,'*':实心五角星,'+':加号。
3)线型属性:'-':实线,'--':虚线,'-.':点划线,':':点线。
label: 关键字参数,设置图例,需要调用plt或子图的legend方法;
linewidth: 关键字参数,设置线的粗细。
4.1 二维可视化图像
import numpy as np
import pylab as pl #该包适合交互式绘图方式
x = np.arange(0.0,2.0*np.pi,0.01)
y = np.cos(x)
y1 = np.sin(x)
pl.plot(x,y,'--')
pl.plot(x,y1)
pl.xlabel('x')
pl.xlabel('y')
pl.title('sin/cos curve')
pl.show()
运行结果如下:
?补充:
import numpy as np
import matplotlib.pyplot as plt
#图像显示中文设置
plt.rcParams['font.sans-serif']=['SimHei']
plt.rcParams['axes.unicode_minus'] = False
X = np.linspace(1,15)
Y = np.sin(X)
plt.figure() #图像的大小可以用来plt.figure(figsize=(10,6))设置,宽:10,高:6
plt.plot(X,Y,'r-*') #绘制X,Y,红色、直线、星型标记
plt.xlabel('X轴')
plt.ylabel('Y轴')
plt.title('y=sin(x)')
plt.grid() #添加网格线
plt.show() #显示图像
运行结果如下:
4.2 一张图中的不同曲线?
import numpy as np
import matplotlib.pyplot as plt
#设置函数的坐标点
x = np.arange(0,2*np.pi,0.01)
y1 = np.sin(x)
y2 = np.cos(x)
#绘制第一个函数曲线
plt.subplot(2,1,1)
plt.plot(x,y1,'b-')
plt.title('sin curve')
#绘制第二个函数曲线
plt.subplot(2,1,2)
plt.plot(x,y2,'g--')
plt.title('cos curve')
plt.show()
运行结果如下:
?4.3 三维曲线图
import matplotlib as mpl
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import matplotlib.pyplot as plt
mpl.rcParams['legend.fontsize'] = 14.5
fig = plt.figure()
ax = fig.gca(projection='3d')
theta = np.linspace(-10*np.pi,10*np.pi,100)
z = np.linspace(-10,10,100)*0.4
r = z**3+1
x = r*np.sin(theta)
y = r*np.cos(theta)
ax.plot(x,y,z,label='parametric curve') #绘制曲线
ax.legend()
plt.show()
运行结果如下:
4.4 其他类型曲线
import numpy as np
import matplotlib.pyplot as plt
#柱状图
plt.subplot(2,2,1)
divisions = ['01','02','03','04','05','06']
divisions_values = [1050,1003,1978,2037,2354,1967]
plt.bar(divisions,divisions_values)
#饼状图
plt.subplot(2,2,2)
language = ['python', 'java','c++','c']
share = [30,32,10,28]
plt.pie(share,labels=language,startangle=45)
plt.axis('equal')
plt.title('pie chart')
#极坐标图
#确定r,θ值
theta = np.linspace(-np.pi,np.pi,100)
r = 2*np.sin(3*theta)
#指定极坐标画图
ax = plt.subplot(2,2,3,projection='polar')
ax.plot(theta,r,color='red')
#散点图
plt.subplot(2,2,4)
N = 15
x = np.random.rand(N)
y = np.random.rand(N)
#每个点随机大小
s = 20*np.random.rand(N)**2
#每个点随机颜色
color = np.random.rand(N)
plt.scatter(x,y,s=s,c=color)
#自动调整图形元素,使其恰当显示
plt.tight_layout()
plt.show()
运行结果如下:
补充:
4.5 三维可视化图像
4.5.1 曲面图绘制
import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
#图像显示中文设置
plt.rcParams['font.sans-serif']=['SimHei']
plt.rcParams['axes.unicode_minus'] = False
#设置图像在可视化时使用的主题
import seaborn as sns
sns.set(font="Kaiti",style="ticks",font_scale=1.4)
#font="Kaiti"参数指定图中文本使用的字体,style="ticks"设置坐标系的样式,font_scale=1.4设置字体的显示比例
#准备要使用的网格数据
x=np.linspace(-4,4,num=50)
y=np.linspace(-4,4,num=50)
X,Y=np.meshgrid(x,y)
Z=np.sin(np.sqrt(X**2+Y**2))
#可视化三维曲面图
fig=plt.figure(figsize=(10,6))
#将坐标系设置为3D坐标系
ax1=fig.add_subplot(111,projection="3d")
#绘制曲面图,rstride:行的跨度,cstride:列的跨度,cmap:颜色,alpha:透明度
ax1.plot_surface(X,Y,Z,rstride=1,cstride=1,alpha=0.5,cmap=plt.cm.coolwarm)
#绘制z轴方向的等高线,投影位置在Z=1的平面
cset = ax1.contour(X,Y,Z,zdir="z",offset=1,cmap=plt.cm.CMRmap)
ax1.set_xlabel("X")
ax1.set_xlim(-4,4)
ax1.set_ylabel("Y")
ax1.set_ylim(-4,4)
ax1.set_zlabel("Z")
ax1.set_zlim(-1,1)
ax1.set_title("曲面图和等高线")
plt.show()
运行结果如下:
4.5.2 曲线图和散点图绘制?
import matplotlib as mpl
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import matplotlib.pyplot as plt
#图像显示中文设置
plt.rcParams['font.sans-serif']=['SimHei']
plt.rcParams['axes.unicode_minus'] = False
#设置图像在可视化时使用的主题
import seaborn as sns
sns.set(font="Kaiti",style="ticks",font_scale=1.4)
#font="Kaiti"参数指定图中文本使用的字体,style="ticks"设置坐标系的样式,font_scale=1.4设置字体的显示比例
#准备数据
theta = np.linspace(-4*np.pi,4*np.pi,100) #角度
z = np.linspace(-2,2,100) #z坐标
r = z**2+1 #半径
x = r*np.sin(theta) #x坐标
y = r*np.cos(theta) #y坐标
#在子图中绘制三维图像
fig=plt.figure(figsize=(10,6))
#将坐标系设置为3D坐标系
ax1=fig.add_subplot(121,projection="3d") #子图1,121代表一行两列第一个
ax1.plot(x,y,z,"b-") #绘制红色三维曲线图
ax1.view_init(elev=20,azim=25) #设置轴的方位角和高程
ax1.set_title("3D曲线图")
ax2=plt.subplot(122,projection="3d") #子图2
ax2.scatter3D(x,y,z,"r",s=20) #绘制红色三维散点图
ax2.view_init(elev=20,azim=25) #设置轴的方位角和高程
ax2.set_title("3D散点图")
plt.subplots_adjust(wspace=0.1) #调整子图像之间的空间距离
plt.show()
运行结果如下:
?4.6 可视化图片(女神)
针对图像数据,可以使用plt.imshow()函数进行可视化,同时针对灰度图像,可以使用参数cmap=plt.cm.gray定义图像的颜色映射,针对一张图片可视化RGB图像和灰度图像的程序如下:
import matplotlib.pyplot as plt
from skimage.io import imread #从skimage库中引入读取图片的函数
from skimage.color import rgb2gray #从skimage库中引入将RGB图片转化为灰度图像的函数
im = imread("E:/PYTHON/liuyifei61a14b8.jpg")
imgray = rgb2gray(im)
#可视化图片
plt.figure(figsize=(10,6))
plt.subplot(1,2,1)
plt.imshow(im)
plt.axis('off') #不显示坐标轴
plt.title('RGB Image')
plt.subplot(1,2,2)
plt.imshow(imgray,cmap=plt.cm.gray)
plt.axis('off')
plt.title('Gray Image')
plt.show()
运行结果如下:(此种情况下对使用刘亦菲女士的照片有点冒犯,再次致歉,但是两张图片都好看)
笔记摘自:《Python机器学习教程》——顾涛
|