一、pandas入门
1. pandas有什么用
- pandas是一个数据分析工具,但是Numpy已经能够帮助我们处理数据,能够结合matplotlib解决部分数据展示等问题,那么pandas学习的目的在什么地方呢
- 增强图表可读性,比如我们想打印出类似成绩单一样的数据,行和列有明文表示的意义
- 便捷的数据处理能力,如:可以通过一行代码将NaN修改过来,也可以处理其他类型的数据(如字符串、时间类型等)
- 读取文件方便
- 封装了matplotlib、numpy的画图和计算
2. pandas的数据结构
- Pandas中一共有三种数据结构,分别为:Series、DataFrame和Multilndex(老版本中叫Panel)
- 其中Series是一维数据结构,DataFrame是二维的表格型数据结构,Multiindex是三维的数据结构
二、Series
- Series是一个类似于一维数组的数据结构,它能够保存任何类型的数据,比如整数、字符串、浮点数等,主要由一组数据和与之相关的索引两部分构成
1. Series的创建
import pandas as pd
# 语法:
pd.Series(data=None,index=None,dtype=None)
"""
参数:
data:传入的数据,可以是ndarray、list等
index:索引,必须是唯一的,且与数据的长度相等。如果没有传入索引参数,则默认会自动创建一个从0-N的整数索引。
dtype:数据的类型,不写则pandas会自动识别
"""
(1)通过指定的数据创建
import pandas as pd
import numpy as np
a1 = pd.Series(data=None,index=None,dtype=None)
a2 = pd.Series(np.arange(10))
print(a1)
print('2'*10)
print(a2) # 第一列是索引,第二列是值
"""
Series([], dtype: float64)
2222222222
0 0
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
dtype: int32
"""
(2)创建时指定索引
- 索引可以随便指定其数据类型
- 注意:索引长度必须与数据的长度相同
b = pd.Series([6.7,5.6,3,10,2],index=[1,2,3,4,5])
b1 = pd.Series([6.7,5.6,3,10,2],index=['s','f','g',4,5])
print(b)
print(b1)
"""
1 6.7
2 5.6
3 3.0
4 10.0
5 2.0
dtype: float64
s 6.7
f 5.6
g 3.0
4 10.0
5 2.0
dtype: float64
"""
(3)通过字典创建
c = pd.Series({'red':100,'blue':200, 'green': 500, 'yellow':1000})
print(c)
"""
red 100
blue 200
green 500
yellow 1000
dtype: int64
"""
2. Series的属性
- 为了更方便地操作Series对象中的索引和数据,Series中提供了两个属性index和values
(1)index 属性
c = pd.Series({'red':100,'blue':200, 'green': 500, 'yellow':1000})
print(c)
print(c.index) # 结果是一个列表,可以通过索引取值
print(c.index[0])
"""
red 100
blue 200
green 500
yellow 1000
dtype: int64
Index(['red', 'blue', 'green', 'yellow'], dtype='object')
red
"""
(2)values 属性
c = pd.Series({'red':100,'blue':200, 'green': 500, 'yellow':1000})
print(c)
print(c.values) # 结果是一个列表,可以通过索引取值
print(c.values[0])
"""
red 100
blue 200
green 500
yellow 1000
dtype: int64
[ 100 200 500 1000]
100
"""
3. Series取值
- 可以通过索引下标取值(0~n),也可以用key取值(类似字典的取值)
import pandas as pd
color_count = pd.Series({'red':100,'blue':200, 'green': 500, 'yellow':1000})
print(color_count[2]) # 500
print(color_count['red']) # 100
三、DataFrame
- DataFrame是一个类似于二维数组或表格(如excel)的对象,既有行索引,又有列索引
- 行索引,表明不同行,叫index,0轴,axis=0,垂直方向
- 列索引,表名不同列,叫columns,1轴,axis=1,水平方向
1. DataFrame的创建
import pandas as pd
# 语法:
pd.DataFrame(data=None,index=None,columns=None)
"""
参数:
index:行标签。如果没有传入索引参数,则默认会自动创建一个从0-N的整数索引。
columns:列标签。如果没有传入索引参数,则默认会自动创建一个从0-N的整数索引
"""
(1)通过指定数据创建
- 回忆直接使用np创建的数组显示方式,比较两者的区别,显然pd创建的更直观可读
print(np.arange(12).reshape(3,4))
d = pd.DataFrame(np.arange(12).reshape(3,4))
print(d)
"""
[[ 0 1 2 3]
[ 4 5 6 7]
[ 8 9 10 11]]
0 1 2 3
0 0 1 2 3
1 4 5 6 7
2 8 9 10 11
"""
(2)创建学生成绩单
# 生成10名同学,5门功课的数据
score_array =np.random.randint(40,100,(10,5))
print(score_array)
no_index_score = pd.DataFrame(score_array)
print(no_index_score)
"""
[[84 48 72 40 65]
[40 67 94 75 72]
[89 75 71 71 73]
[44 41 81 78 55]
[91 99 71 45 87]
[41 63 63 76 78]
[72 90 50 56 45]
[85 87 55 56 51]
[77 99 43 76 77]
[42 71 62 57 55]]
0 1 2 3 4
0 84 48 72 40 65
1 40 67 94 75 72
2 89 75 71 71 73
3 44 41 81 78 55
4 91 99 71 45 87
5 41 63 63 76 78
6 72 90 50 56 45
7 85 87 55 56 51
8 77 99 43 76 77
9 42 71 62 57 55
"""
(3)创建时指定索引
- 上面我们虽然创建了成绩单,但是行和列代表的意义却不清楚,下面我们加上行和列的索引,再看看
- 指定的索引index必须和行数相同,columns必须和列数相同
import pandas as pd
# 生成10名同学,5门功课的数据
score_array =np.random.randint(40,100,(10,5))
# print(score_array)
no_index_score = pd.DataFrame(score_array)
# print(no_index_score)
# 构造行索引序列
xueke =["语文","数学","英语","政治","体育"]
# 构造列索引序列
stu =['同学'+str(i) for i in range(no_index_score.shape[0])] # no_index_score.shape[0] 获取总共的行数
#添加行、列索引
data = pd.DataFrame(score_array,columns=xueke, index=stu)
print(data)
"""
语文 数学 英语 政治 体育
同学0 49 84 75 66 65
同学1 55 67 52 85 69
同学2 65 78 94 97 59
同学3 73 45 46 83 65
同学4 85 66 73 51 64
同学5 46 74 68 93 88
同学6 62 79 51 86 90
同学7 69 99 65 70 45
同学8 86 54 79 48 50
同学9 65 40 56 55 52
"""
2. DataFrame的属性
- DataFrame对象提供了下面7种属性
- shape,实际就是获取二维数组的形状
- index,获取数据的纵向上的索引,结果是个列表,可以对其索引取值
- columns,获取数据的横向上的索引,结果是个列表,可以对其索引取值
- values,获取初始的二维数组数据
- T,就是数组的转置效果一样
(1)展开部分数据
head(n),显示前n行内容,n不写默认5,显示的内容是携带所在的index和columns的
tail(n),显示后n行内容,n不写默认5,显示的内容是携带所在的index和columns的
sample(n),从数据中随机采样得到n个样本。n不写默认5,显示的内容是携带所在的index和columns的
(2)示例
# 生成10名同学,5门功课的数据
score_array =np.random.randint(40,100,(10,5))
# print(score_array)
no_index_score = pd.DataFrame(score_array)
# print(no_index_score)
# 构造行索引序列
xueke =["语文","数学","英语","政治","体育"]
# 构造列索引序列
stu =['同学'+str(i) for i in range(no_index_score.shape[0])] # no_index_score.shape[0] 获取总共的行数
#添加行索引
data = pd.DataFrame(score_array,columns=xueke, index=stu)
# print(data)
print(data.shape)
print(data.index)
print(data.columns)
print(data.values) # 结果是一个二维数组
print(data.T)
print(data.head())
print(data.tail())
"""
(10, 5)
Index(['同学0', '同学1', '同学2', '同学3', '同学4', '同学5', '同学6', '同学7', '同学8', '同学9'], dtype='object')
Index(['语文', '数学', '英语', '政治', '体育'], dtype='object')
[[55 71 62 89 50]
[42 66 69 45 48]
[90 81 99 85 42]
[80 70 79 48 69]
[58 68 89 79 51]
[44 66 53 70 48]
[89 46 82 94 75]
[68 71 61 83 42]
[92 95 46 82 47]
[65 48 55 92 62]]
同学0 同学1 同学2 同学3 同学4 同学5 同学6 同学7 同学8 同学9
语文 69 97 48 71 91 92 97 56 50 89
数学 51 85 89 80 49 94 92 83 45 59
英语 97 91 97 58 45 97 48 43 43 55
政治 57 68 69 62 57 87 62 68 71 93
体育 58 57 73 60 45 95 46 54 66 57
语文 数学 英语 政治 体育
同学0 40 48 82 44 75
同学1 80 86 84 70 70
同学2 61 91 52 62 47
同学3 83 43 81 60 62
同学4 99 77 45 89 97
语文 数学 英语 政治 体育
同学5 51 88 96 53 53
同学6 95 93 55 56 55
同学7 83 42 48 40 42
同学8 46 67 44 83 43
同学9 78 63 96 53 50
"""
3. DataFrame的索引操作
(1)修改索引值
stu=["学生_"+str(i) for i in range(no_index_score.shape[0])]
data.index= stu
print(data)
"""
语文 数学 英语 政治 体育
学生_0 95 80 76 80 86
学生_1 80 45 79 96 50
学生_2 66 70 82 93 99
学生_3 46 50 86 57 40
学生_4 65 46 92 82 88
学生_5 66 88 95 53 78
学生_6 77 45 81 47 81
学生_7 76 79 85 47 42
学生_8 78 81 91 63 54
学生_9 55 45 41 42 43
"""
#错误修改方式
data.index[3]='学生_3' # 直接报错
(2)重置索引
# 语法:
reset_index(drop=False)
# 设置新的下标索引
- drop:默认为False,不删除原来索引,如果为True,删除原来的索引值
print(data)
print(data.index)
#重置索引,drop=False
data1 = data.reset_index()
print(data1)
print(data1.index)
#重置索引,drop=True
data2 = data.reset_index(drop=True)
print(data2)
print(data2.index)
"""
语文 数学 英语 政治 体育
学生_0 98 51 83 76 58
学生_1 81 94 48 97 67
学生_2 61 64 85 89 72
学生_3 76 60 51 57 72
学生_4 58 54 54 60 44
学生_5 76 76 67 69 62
学生_6 79 65 83 75 89
学生_7 52 94 55 65 88
学生_8 77 83 65 46 63
学生_9 99 85 57 44 41
Index(['学生_0', '学生_1', '学生_2', '学生_3', '学生_4', '学生_5', '学生_6', '学生_7', '学生_8',
'学生_9'],
dtype='object')
index 语文 数学 英语 政治 体育
0 学生_0 98 51 83 76 58
1 学生_1 81 94 48 97 67
2 学生_2 61 64 85 89 72
3 学生_3 76 60 51 57 72
4 学生_4 58 54 54 60 44
5 学生_5 76 76 67 69 62
6 学生_6 79 65 83 75 89
7 学生_7 52 94 55 65 88
8 学生_8 77 83 65 46 63
9 学生_9 99 85 57 44 41
RangeIndex(start=0, stop=10, step=1)
语文 数学 英语 政治 体育
0 98 51 83 76 58
1 81 94 48 97 67
2 61 64 85 89 72
3 76 60 51 57 72
4 58 54 54 60 44
5 76 76 67 69 62
6 79 65 83 75 89
7 52 94 55 65 88
8 77 83 65 46 63
9 99 85 57 44 41
RangeIndex(start=0, stop=10, step=1)
"""
(3)以某列值设置为新的索引
- 可以指定某一列或同时指定某几列的值为index索引
- 注意:若是指定两列为index索引,这样DataFrame就变成了一个具有Multiindex的DataFrame
# 语法:
set_index(keys, drop=True)
- keys:列索引名成或者列索引名称的列表
- drop:boolean,default True.当做新的索引,删除原来的列
1. 将月份的值设定为index索引
df = pd.DataFrame({'month':[1,4,7,10],
'year':[2012,2014,2013,2014],
'sale':[55,40,84,31]})
print(df)
print(df.index)
df1 = df.set_index('month')
print(df1)
print(df1.index)
"""
month year sale
0 1 2012 55
1 4 2014 40
2 7 2013 84
3 10 2014 31
RangeIndex(start=0, stop=4, step=1)
year sale
month
1 2012 55
4 2014 40
7 2013 84
10 2014 31
Int64Index([1, 4, 7, 10], dtype='int64', name='month')
"""
2. 设置多个索引,以年和月份
df2 = df.set_index(['year','month']) # 通过这样的设置,df2就变成了一个具有Multiindex的DataFrame
print(df2)
print(df2.index)
"""
sale
year month
2012 1 55
2014 4 40
2013 7 84
2014 10 31
MultiIndex([(2012, 1),
(2014, 4),
(2013, 7),
(2014, 10)],
names=['year', 'month'])
"""
四、Multilndex与Panel
- Multilndex是三维的数据结构
- 多级索引(也称层次化索引)是pandas的重要功能,可以在Series、DataFrame对象上拥有2个以及2个以上的索引
1. multilndex的index特性
df2 = df.set_index(['year','month']) # 通过这样的设置,df2就变成了一个具有Multiindex的DataFrame
print(df2)
print(df2.index)
"""
sale
year month
2012 1 55
2014 4 40
2013 7 84
2014 10 31
MultiIndex([(2012, 1),
(2014, 4),
(2013, 7),
(2014, 10)],
names=['year', 'month'])
"""
# 可以看到df2.index是一个多级或分层索引对象
- index包含两个属性,names和levels
- names:包含的元素是levels的名称
- levels:包含元素的是每个level的元组值
print(df2.index.names)
print(df2.index.levels)
"""
['year', 'month']
[[2012, 2013, 2014], [1, 4, 7, 10]]
"""
2. multilndex的创建
- 通过上面的特性,我们知道multilndex的创建要指定两个东西:index的names和levels
arrays = [[1,1,2,2],['red','blue','red','blue']]
ml = pd.MultiIndex.from_arrays(arrays,names=("num","col"))
print(ml)
"""
MultiIndex([(1, 'red'),
(1, 'blue'),
(2, 'red'),
(2, 'blue')],
names=['num', 'col'])
"""
五、pandas读取、保存文件
- pandas的API支持众多的文件格式如CSV、SQL、XLS、JSON、HDF5
- 注:最常用的HDF5和CSV文件
1. CSV文件
# 1. 读取
pandas.read_csv(filepath_or_buffer, sep =',')
- filepath_or_buffer:文件路径
- usecols:指定读取的列名,usecols为列表格式
# 示例
# 读取文件,并且指定只读取'open','close'指标
data = pd.read_csv("./data/stock_day.csv", usecols=['open', 'close'])
# 2. 保存
DataFrame.to_csv(path_or_buf=None, sep=',’, columns=None, header=True, index=True, mode='w',encoding=None)
path_or_buf :文件路径
sep :分隔符,默认用","隔开
columns :选择需要的列索引
header :boolean or list of string,default True,是否写进列索引值
index:是否写进行索引
mode:'w':重写,'a'追加
# 示例
# 选取10行数据保存,便于观察数据
data[:10].to_csv("./data/test.csv",columns=['open']) # 这样会把index索引也当作一列保存到文件中
# 参数index=False 存储不会将索引值变成一列数据
data[:10].to_csv("./data/test.csv", columns=['open'], index=False)
2. HDF5文件
- HDF5文件的读取和存储需要指定一个键,值为要存储的DataFrame
- 避免不能读取HDF5文件,需要安装安装tables模块
pip install tables
- 注意:pandas优先选择使用HDF5文件存储
- HDF5在存储的时候支持压缩,使用的方式是blosc,这个是速度最快的也是pandas默认支持的
- 使用压缩可以提磁盘利用率,节省空间
- HDF5还是跨平台的,可以轻松迁移到hadoop上面
# 1. 读取
pandas.read_hdf(path_or_buf, key =None,**kwargs)
path_or_buffer:文件路径
key:读取的键
return:Theselected object
# 2. 保存
DataFrame.to_hdf(path_or_buf, key)