pandas学习笔记(三):数据的变换与数据的管理

注:学习笔记基于文彤老师的pandas的系列课程

课程链接:https://study.163.com/course/courseMain.htm?courseId=1005124008&share=1&shareId=1146477588

# 设定系统环境
import pandas as pd
pd.options.display.max_rows = 10 # 设定自由列表输出最多为10行
pd.__version__ # 显示当前Pandas版本号,默认输出最后一行内容(即使没有打印输出)
'1.1.0'
df2 = pd.read_csv("univ.csv", encoding ="GBK")#使用英文名称,否则可能会报错
#把文件放到了该目录下,因此不需要再写路径,注意编码要写
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门
01北京大学100.00综合北京北京市中国研究型教育部
12清华大学98.50理工北京北京市中国研究型教育部
23复旦大学82.79综合上海上海市中国研究型教育部
34武汉大学82.43综合湖北武汉市中国研究型教育部
45浙江大学82.38综合浙江杭州市中国研究型教育部
...........................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
9697安徽大学63.34综合安徽合肥市区域研究型安徽省
9798首都医科大学63.32医药北京北京市区域特色研究型北京市
9899江南大学63.31综合江苏无锡市区域特色研究型教育部
99100山西大学63.29综合山西太原市区域研究型山西省

100 rows × 8 columns

1.变量变换

1.1计算新变量

新变量为常数

df[‘varname’] = value

df2.newvar = 1 # 注意该命令不会报错,但是这是错误写法
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门
01北京大学100.00综合北京北京市中国研究型教育部
12清华大学98.50理工北京北京市中国研究型教育部
23复旦大学82.79综合上海上海市中国研究型教育部
34武汉大学82.43综合湖北武汉市中国研究型教育部
45浙江大学82.38综合浙江杭州市中国研究型教育部
...........................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
9697安徽大学63.34综合安徽合肥市区域研究型安徽省
9798首都医科大学63.32医药北京北京市区域特色研究型北京市
9899江南大学63.31综合江苏无锡市区域特色研究型教育部
99100山西大学63.29综合山西太原市区域研究型山西省

100 rows × 8 columns

df2['cons'] = 1
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门cons
01北京大学100.00综合北京北京市中国研究型教育部1
12清华大学98.50理工北京北京市中国研究型教育部1
23复旦大学82.79综合上海上海市中国研究型教育部1
34武汉大学82.43综合湖北武汉市中国研究型教育部1
45浙江大学82.38综合浙江杭州市中国研究型教育部1
..............................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省1
9697安徽大学63.34综合安徽合肥市区域研究型安徽省1
9798首都医科大学63.32医药北京北京市区域特色研究型北京市1
9899江南大学63.31综合江苏无锡市区域特色研究型教育部1
99100山西大学63.29综合山西太原市区域研究型山西省1

100 rows × 9 columns

基于原变量做简单四则运算
df[‘varname’] = df[‘oldvar’] * 100
df[‘varname’] = df.oldvar * 100

df2['new2'] = df2.总分 + df2.名次 + 1#new2可以不存在,若存在,则进行重新赋值
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门consnew2
01北京大学100.00综合北京北京市中国研究型教育部1102.00
12清华大学98.50理工北京北京市中国研究型教育部1101.50
23复旦大学82.79综合上海上海市中国研究型教育部186.79
34武汉大学82.43综合湖北武汉市中国研究型教育部187.43
45浙江大学82.38综合浙江杭州市中国研究型教育部188.38
.................................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省1160.37
9697安徽大学63.34综合安徽合肥市区域研究型安徽省1161.34
9798首都医科大学63.32医药北京北京市区域特色研究型北京市1162.32
9899江南大学63.31综合江苏无锡市区域特色研究型教育部1163.31
99100山西大学63.29综合山西太原市区域研究型山西省1164.29

100 rows × 10 columns

import numpy
df2.new2 = numpy.sqrt(df2.总分) # numpy内置函数自动支持serial格式数据
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门consnew2
01北京大学100.00综合北京北京市中国研究型教育部110.000000
12清华大学98.50理工北京北京市中国研究型教育部19.924717
23复旦大学82.79综合上海上海市中国研究型教育部19.098901
34武汉大学82.43综合湖北武汉市中国研究型教育部19.079097
45浙江大学82.38综合浙江杭州市中国研究型教育部19.076343
.................................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.960528
9697安徽大学63.34综合安徽合肥市区域研究型安徽省17.958643
9798首都医科大学63.32医药北京北京市区域特色研究型北京市17.957387
9899江南大学63.31综合江苏无锡市区域特色研究型教育部17.956758
99100山西大学63.29综合山西太原市区域研究型山西省17.955501

100 rows × 10 columns

# import math
# df2['new3'] = math.sqrt(df2.总分) # 此处会报错,因为math中只支持对浮点数操作
#可以借助下面的进行变换
# df2

基于一个原变量做函数运算
df.apply(

func : 希望对行/列执行的函数表达式

axis = 0 : 针对行还是列进行计算
(0/‘index’: 针对每列进行计算
1/‘columns’: 针对每行进行计算)

)

简化的用法

df[‘varname’] = df.oldvar.apply(函数表达式)

import math
df2['new3'] = df2.总分.apply(math.sqrt)
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01北京大学100.00综合北京北京市中国研究型教育部110.00000010.000000
12清华大学98.50理工北京北京市中国研究型教育部19.9247179.924717
23复旦大学82.79综合上海上海市中国研究型教育部19.0989019.098901
34武汉大学82.43综合湖北武汉市中国研究型教育部19.0790979.079097
45浙江大学82.38综合浙江杭州市中国研究型教育部19.0763439.076343
....................................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 11 columns

df2['new3'] = df2.总分.apply(numpy.sqrt)#numpy不用apply也可以实现,它默认
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01北京大学100.00综合北京北京市中国研究型教育部110.00000010.000000
12清华大学98.50理工北京北京市中国研究型教育部19.9247179.924717
23复旦大学82.79综合上海上海市中国研究型教育部19.0989019.098901
34武汉大学82.43综合湖北武汉市中国研究型教育部19.0790979.079097
45浙江大学82.38综合浙江杭州市中国研究型教育部19.0763439.076343
....................................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 11 columns

对所有单元格进行相同的函数运算

dfnew = df.applymap(函数表达式) # 是以cell为单位在进行操作

df2[['名次', '总分']].applymap(math.sqrt)
名次总分
01.00000010.000000
11.4142149.924717
21.7320519.098901
32.0000009.079097
42.2360689.076343
.........
959.7979597.960528
969.8488587.958643
979.8994957.957387
989.9498747.956758
9910.0000007.955501

100 rows × 2 columns

不修改原df,而是生成新的df

df.assign(varname = expression)

df3 = df2.assign(new = df2.总分.apply(math.sqrt))
df3
名次学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3new
01北京大学100.00综合北京北京市中国研究型教育部110.00000010.00000010.000000
12清华大学98.50理工北京北京市中国研究型教育部19.9247179.9247179.924717
23复旦大学82.79综合上海上海市中国研究型教育部19.0989019.0989019.098901
34武汉大学82.43综合湖北武汉市中国研究型教育部19.0790979.0790979.079097
45浙江大学82.38综合浙江杭州市中国研究型教育部19.0763439.0763439.076343
.......................................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.9605287.960528
9697安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.9586437.958643
9798首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.9573877.957387
9899江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.9567587.956758
99100山西大学63.29综合山西太原市区域研究型山西省17.9555017.9555017.955501

100 rows × 12 columns

1.2在指定位置插入新变量列

df.insert(

loc : 插入位置的索引值,0 <= loc <= len(columns)#即在最后加

column : 插入的新列名称

value : Series或者类数组结构的变量值

allow_duplicates = False : 是否允许新列重名

) # 该方法会直接修改原df

df2.insert(1,'newvar','cons')#与其默认变量属性一一对应
df2
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学100.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学98.50理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学82.79综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学82.43综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学82.38综合浙江杭州市中国研究型教育部19.0763439.076343
.......................................
9596cons浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697cons安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798cons首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899cons江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100cons山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 12 columns

1.3修改/替换变量值

本质上是如何直接指定到单元格的问题,只要能准确定位单元格地址,就能够做到准确替换。

df2.所在城市.isin(['上海'])
0     False
1     False
2     False
3     False
4     False
      ...  
95    False
96    False
97    False
98    False
99    False
Name: 所在城市, Length: 100, dtype: bool
df2.所在城市[70] = '上海市' # 这种引用方式会给出警告,因为其把【】当成切片,
                             #赋值会不恰当
df2[69:75]
D:\anaconda3\lib\site-packages\ipykernel_launcher.py:1: SettingWithCopyWarning: 
A value is trying to be set on a copy of a slice from a DataFrame

See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy
  """Entry point for launching an IPython kernel.
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
6970cons第三军医大学64.81医药重庆重庆行业特色研究型18.0504668.050466
7071cons第二军医大学64.74医药上海上海市行业特色研究型18.0461178.046117
7172cons湖南师范大学64.65师范湖南长沙市区域研究型湖南省18.0405228.040522
7273cons第四军医大学64.51医药陕西西安行业特色研究型18.0318128.031812
7374cons华南师范大学64.42师范广东广州市区域特色研究型广东省18.0262078.026207
7475cons上海大学64.41综合上海上海市区域研究型上海市18.0255848.025584
df2['所在城市'][70] = '上海市' # 这种引用方式会给出警告
df2[69:75]
D:\anaconda3\lib\site-packages\ipykernel_launcher.py:1: SettingWithCopyWarning: 
A value is trying to be set on a copy of a slice from a DataFrame

See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy
  """Entry point for launching an IPython kernel.
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
6970cons第三军医大学64.81医药重庆重庆行业特色研究型18.0504668.050466
7071cons第二军医大学64.74医药上海上海市行业特色研究型18.0461178.046117
7172cons湖南师范大学64.65师范湖南长沙市区域研究型湖南省18.0405228.040522
7273cons第四军医大学64.51医药陕西西安行业特色研究型18.0318128.031812
7374cons华南师范大学64.42师范广东广州市区域特色研究型广东省18.0262078.026207
7475cons上海大学64.41综合上海上海市区域研究型上海市18.0255848.025584
df2.loc[70, '所在城市'] = '上海市' # 精确引用,消停了,注意loc是相对索引的70
df2
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学100.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学98.50理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学82.79综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学82.43综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学82.38综合浙江杭州市中国研究型教育部19.0763439.076343
.......................................
9596cons浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697cons安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798cons首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899cons江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100cons山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 12 columns

对应数值的替换
df.replace
(

to_replace = None : 将被替换的原数值,所有严格匹配的数值将被用value替换(可以是str/regex/list/dict/Series/numeric/None)

value = None : 希望填充的新数值

inplace = False

)

df2.所在城市.replace('北京市', '帝都')# 单个值替换
0      帝都
1      帝都
2     上海市
3     武汉市
4     杭州市
     ... 
95    金华市
96    合肥市
97     帝都
98    无锡市
99    太原市
Name: 所在城市, Length: 100, dtype: object
df2.所在城市.replace(['北京市', '上海市'], ['帝都', '魔都']) # 列表值批量替换 
0      帝都
1      帝都
2      魔都
3     武汉市
4     杭州市
     ... 
95    金华市
96    合肥市
97     帝都
98    无锡市
99    太原市
Name: 所在城市, Length: 100, dtype: object
# 字典批量映射替换 
df2.所在城市.replace({'北京市' : '帝都',  '上海市' : '魔都'}) 
0      帝都
1      帝都
2      魔都
3     武汉市
4     杭州市
     ... 
95    金华市
96    合肥市
97     帝都
98    无锡市
99    太原市
Name: 所在城市, Length: 100, dtype: object

指定数值范围的替换

方法一:使用正则表达式完成替换,较复杂,一般不用

df.replace(regex, newvalue)

方法二:使用行筛选方式完成替换

用行筛选方式得到行索引,然后用loc命令定位替换

目前也支持直接筛选出单元格进行数值替换

注意:query命令的类SQL语句可以进行检索,但不直接支持数值替换

df2.总分.iloc[0:2] = 10#这些都是直接在df2上进行修改了
df2
C:\Users\lenovo\AppData\Roaming\Python\Python36\site-packages\pandas\core\indexing.py:670: SettingWithCopyWarning: 
A value is trying to be set on a copy of a slice from a DataFrame

See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy
  iloc._setitem_with_indexer(indexer, value)
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学10.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学10.00理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学82.79综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学82.43综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学82.38综合浙江杭州市中国研究型教育部19.0763439.076343
.......................................
9596cons浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697cons安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798cons首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899cons江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100cons山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 12 columns

df2.loc[3:5,'总分'] = 20
df2.head(10)
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学10.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学10.00理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学82.79综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学20.00综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学20.00综合浙江杭州市中国研究型教育部19.0763439.076343
56cons中国人民大学20.00综合北京北京市中国研究型教育部19.0542819.054281
67cons上海交通大学81.76综合上海上海市中国研究型教育部19.0421249.042124
78cons南京大学80.43综合江苏南京市中国研究型教育部18.9682778.968277
89cons国防科学技术大学80.31理工湖南长沙市中国研究型中央军委18.9615858.961585
910cons中山大学76.46综合广东广州市中国研究型教育部18.7441418.744141
# 用loc命令完成替换
df2.loc[df2[df2.名次 < 10].index, '总分'] = 20 # 用index引用出相应的索引
df2.head(10)
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学20.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学20.00理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学20.00综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学20.00综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学20.00综合浙江杭州市中国研究型教育部19.0763439.076343
56cons中国人民大学20.00综合北京北京市中国研究型教育部19.0542819.054281
67cons上海交通大学20.00综合上海上海市中国研究型教育部19.0421249.042124
78cons南京大学20.00综合江苏南京市中国研究型教育部18.9682778.968277
89cons国防科学技术大学20.00理工湖南长沙市中国研究型中央军委18.9615858.961585
910cons中山大学76.46综合广东广州市中国研究型教育部18.7441418.744141
# index可以省去
df2.loc[df2.名次 < 10, '总分'] = 20
df2.head(10)
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学20.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学20.00理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学20.00综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学20.00综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学20.00综合浙江杭州市中国研究型教育部19.0763439.076343
56cons中国人民大学20.00综合北京北京市中国研究型教育部19.0542819.054281
67cons上海交通大学20.00综合上海上海市中国研究型教育部19.0421249.042124
78cons南京大学20.00综合江苏南京市中国研究型教育部18.9682778.968277
89cons国防科学技术大学20.00理工湖南长沙市中国研究型中央军委18.9615858.961585
910cons中山大学76.46综合广东广州市中国研究型教育部18.7441418.744141
# 直接进行定位和替换
df2.总分[df2.名次 < 10] = 25
df2
D:\anaconda3\lib\site-packages\ipykernel_launcher.py:2: SettingWithCopyWarning: 
A value is trying to be set on a copy of a slice from a DataFrame

See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学25.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学25.00理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学25.00综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学25.00综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学25.00综合浙江杭州市中国研究型教育部19.0763439.076343
.......................................
9596cons浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697cons安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798cons首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899cons江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100cons山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 12 columns

# 注意这里的出错原因,先选行则知识一个拷贝,原本没有任何变化
#不推荐这样使用,就记住要先选列在选行,即为上面的做法,最优的为上面的上面的做法
#df2[df2.名次 < 10].总分 = 30
#df2
#下面的类SQL也是同理
# query语句无法直接实现数值替换,原因:query生成的是数据copy,不是地址引用
#df2.query("名次 < 10 and 类型 != '综合'")['总分'] = 25
#df2
# query语句可以用于index定位,然后实现数值替换
df2.loc[df2.query("名次 < 10 and 类型 == '综合'").index, '总分'] = 10
df2
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学10.00综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学25.00理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学10.00综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学10.00综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学10.00综合浙江杭州市中国研究型教育部19.0763439.076343
.......................................
9596cons浙江师范大学63.37师范浙江金华市区域特色研究型浙江省17.9605287.960528
9697cons安徽大学63.34综合安徽合肥市区域研究型安徽省17.9586437.958643
9798cons首都医科大学63.32医药北京北京市区域特色研究型北京市17.9573877.957387
9899cons江南大学63.31综合江苏无锡市区域特色研究型教育部17.9567587.956758
99100cons山西大学63.29综合山西太原市区域研究型山西省17.9555017.955501

100 rows × 12 columns

1.4 哑变量变换

pd.get_dummies(

data : 希望转换的数据框/变量列

prefix = None : 哑变量名称前缀

prefix_____seq = “_________”: 前缀和序号之间的连接字符,设定有prefix或列名时生效

dummy__na = False : 是否为NaNs专门设定一个哑变量列

columns = None : 希望转换的原始列名,如果不设定,则转换所有符合条件的列

drop__first = False : 是否返回k-1个哑变量,而不是k个哑变量

) # 返回值为数据框

注意:被转换为哑变量的相应原始列会被自动删除。

df2.head()
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3
01cons北京大学10.0综合北京北京市中国研究型教育部110.00000010.000000
12cons清华大学25.0理工北京北京市中国研究型教育部19.9247179.924717
23cons复旦大学10.0综合上海上海市中国研究型教育部19.0989019.098901
34cons武汉大学10.0综合湖北武汉市中国研究型教育部19.0790979.079097
45cons浙江大学10.0综合浙江杭州市中国研究型教育部19.0763439.076343
pd.get_dummies(df2.类型, prefix = "pre" )
pre_农林pre_医药pre_师范pre_政法pre_民族pre_理工pre_综合pre_财经
000000010
100000100
200000010
300000010
400000010
...........................
9500100000
9600000010
9701000000
9800000010
9900000010

100 rows × 8 columns

pd.get_dummies(df2, columns=['类型'] )#直接将两个表连接在了一起
名次newvar学校名称总分所在省份所在城市办学方向主管部门consnew2new3类型_农林类型_医药类型_师范类型_政法类型_民族类型_理工类型_综合类型_财经
01cons北京大学10.00北京北京市中国研究型教育部110.00000010.00000000000010
12cons清华大学25.00北京北京市中国研究型教育部19.9247179.92471700000100
23cons复旦大学10.00上海上海市中国研究型教育部19.0989019.09890100000010
34cons武汉大学10.00湖北武汉市中国研究型教育部19.0790979.07909700000010
45cons浙江大学10.00浙江杭州市中国研究型教育部19.0763439.07634300000010
............................................................
9596cons浙江师范大学63.37浙江金华市区域特色研究型浙江省17.9605287.96052800100000
9697cons安徽大学63.34安徽合肥市区域研究型安徽省17.9586437.95864300000010
9798cons首都医科大学63.32北京北京市区域特色研究型北京市17.9573877.95738701000000
9899cons江南大学63.31江苏无锡市区域特色研究型教育部17.9567587.95675800000010
99100cons山西大学63.29山西太原市区域研究型山西省17.9555017.95550100000010

100 rows × 19 columns

1.5数值变量分段

pd.cut(

x : 希望进行分段的变量列名称

bins : 具体的分段设定

int :被等距等分的段数

sequence of scalars :具体的每一个分段起点,必须包括最值,可不等距

right = True : 每段是否包括右侧界值

labels = None : 为每个分段提供自定义标签

include_lowest = False : 第一段是否包括最左侧界值,需要和right参数配合

) # 分段结果是数值类型为Categories的序列

pd.qcut() # 按照频数,而不是按照取值范围进行等分

df2['cls'] = pd.cut(df2.名次, bins=[1,3,7], 
                    right= True, include_lowest = True)
df2.head(10)
名次newvar学校名称总分类型所在省份所在城市办学方向主管部门consnew2new3cls
01cons北京大学10.00综合北京北京市中国研究型教育部110.00000010.000000(0.999, 3.0]
12cons清华大学25.00理工北京北京市中国研究型教育部19.9247179.924717(0.999, 3.0]
23cons复旦大学10.00综合上海上海市中国研究型教育部19.0989019.098901(0.999, 3.0]
34cons武汉大学10.00综合湖北武汉市中国研究型教育部19.0790979.079097(3.0, 7.0]
45cons浙江大学10.00综合浙江杭州市中国研究型教育部19.0763439.076343(3.0, 7.0]
56cons中国人民大学10.00综合北京北京市中国研究型教育部19.0542819.054281(3.0, 7.0]
67cons上海交通大学10.00综合上海上海市中国研究型教育部19.0421249.042124(3.0, 7.0]
78cons南京大学10.00综合江苏南京市中国研究型教育部18.9682778.968277NaN
89cons国防科学技术大学25.00理工湖南长沙市中国研究型中央军委18.9615858.961585NaN
910cons中山大学76.46综合广东广州市中国研究型教育部18.7441418.744141NaN

实战:进一步整理PM2.5数据

要求:

在数据中剔除PM2.5为-999的案例(均为缺失数据)

建立一个新变量high,当PM2.5 >= 200时为1,否则为0

建立一个新变量high2,按照PM2.5 在100,200,500分为四段,分别取值0,1,2,3

将high2转换为哑变量组

按照50一个组段,将PM2.5数值转换为分段变量high3

bj2012 = pd.read_csv("PM25\Beijing_2012_HourlyPM2.5_created20140325.csv",encoding ="gbk",skiprows=3)#注意sep
bj2012
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Name
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValid
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValid
....................................
8779BeijingPM2.52012-12-31 19:002012123119131礸/mg?1 HrValidNaN
8780BeijingPM2.52012-12-31 20:002012123120113礸/mg?1 HrValidNaN
8781BeijingPM2.52012-12-31 21:00201212312145礸/mg?1 HrValidNaN
8782BeijingPM2.52012-12-31 22:00201212312239礸/mg?1 HrValidNaN
8783BeijingPM2.52012-12-31 23:00201212312335礸/mg?1 HrValidNaN

8784 rows × 11 columns

bj2012[bj2012.Value.isin([-999])]
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Name
321BeijingPM2.52012-1-14 9:0020121149-999礸/mg?1 HrMissingNaN
322BeijingPM2.52012-1-14 10:00201211410-999礸/mg?1 HrMissingNaN
323BeijingPM2.52012-1-14 11:00201211411-999礸/mg?1 HrMissingNaN
324BeijingPM2.52012-1-14 12:00201211412-999礸/mg?1 HrMissingNaN
325BeijingPM2.52012-1-14 13:00201211413-999礸/mg?1 HrMissingNaN
....................................
8695BeijingPM2.52012-12-28 7:00201212287-999礸/mg?1 HrMissingNaN
8696BeijingPM2.52012-12-28 8:00201212288-999礸/mg?1 HrMissingNaN
8697BeijingPM2.52012-12-28 9:00201212289-999礸/mg?1 HrMissingNaN
8698BeijingPM2.52012-12-28 10:002012122810-999礸/mg?1 HrMissingNaN
8699BeijingPM2.52012-12-28 11:002012122811-999礸/mg?1 HrMissingNaN

489 rows × 11 columns

bj2012= bj2012.loc[bj2012.query("Value != '-999'").index]
bj2012
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Name
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValid
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValid
....................................
8779BeijingPM2.52012-12-31 19:002012123119131礸/mg?1 HrValidNaN
8780BeijingPM2.52012-12-31 20:002012123120113礸/mg?1 HrValidNaN
8781BeijingPM2.52012-12-31 21:00201212312145礸/mg?1 HrValidNaN
8782BeijingPM2.52012-12-31 22:00201212312239礸/mg?1 HrValidNaN
8783BeijingPM2.52012-12-31 23:00201212312335礸/mg?1 HrValidNaN

8295 rows × 11 columns

bj2012[bj2012.Value.isin([-999])]#已经清除完毕
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Name
bj2012.loc[bj2012.Value>=200, 'high'] = 1
bj2012.head(10)
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Namehigh
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid1.0
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid1.0
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid1.0
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValidNaN
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValidNaN
5BeijingPM2.52012-1-1 5:00201211523礸/mg?1 HrValidNaN
6BeijingPM2.52012-1-1 6:00201211619礸/mg?1 HrValidNaN
7BeijingPM2.52012-1-1 7:00201211714礸/mg?1 HrValidNaN
8BeijingPM2.52012-1-1 8:00201211816礸/mg?1 HrValidNaN
9BeijingPM2.52012-1-1 9:00201211921礸/mg?1 HrValidNaN
bj2012.loc[bj2012.Value<200, 'high'] = 0
bj2012.head(10)
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Namehigh
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid1.0
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid1.0
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid1.0
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValid0.0
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValid0.0
5BeijingPM2.52012-1-1 5:00201211523礸/mg?1 HrValid0.0
6BeijingPM2.52012-1-1 6:00201211619礸/mg?1 HrValid0.0
7BeijingPM2.52012-1-1 7:00201211714礸/mg?1 HrValid0.0
8BeijingPM2.52012-1-1 8:00201211816礸/mg?1 HrValid0.0
9BeijingPM2.52012-1-1 9:00201211921礸/mg?1 HrValid0.0
bj2012['high2'] = pd.cut(bj2012.Value, bins=[0,100,200,500,9999],labels = [0,1,2,3],
                    right= True, include_lowest = True)
bj2012.head(10)
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Namehighhigh2
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid1.02
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid1.02
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid1.02
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValid0.00
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValid0.00
5BeijingPM2.52012-1-1 5:00201211523礸/mg?1 HrValid0.00
6BeijingPM2.52012-1-1 6:00201211619礸/mg?1 HrValid0.00
7BeijingPM2.52012-1-1 7:00201211714礸/mg?1 HrValid0.00
8BeijingPM2.52012-1-1 8:00201211816礸/mg?1 HrValid0.00
9BeijingPM2.52012-1-1 9:00201211921礸/mg?1 HrValid0.00
pd.get_dummies(bj2012.high2, prefix = "pre" )
pre_0pre_1pre_2pre_3
00010
10010
20010
31000
41000
...............
87790100
87800100
87811000
87821000
87831000

8295 rows × 4 columns

bj2012['high3'] = pd.cut(bj2012.Value, bins=50,
                    right= True, include_lowest = True)
bj2012.head()
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Namehighhigh2high3
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid1.02(298.2, 318.08]
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid1.02(198.8, 218.68]
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid1.02(218.68, 238.56]
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValid0.00(79.52, 99.4]
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValid0.00(19.88, 39.76]

2.文件级别的数据管理

2.1 数据拆分

标记数据拆分组

df.groupby(

by : 用于分组的变量名/函数

axis = 0 :

level = None : 相应的轴存在多重索引时,指定用于分组的级别

as_index = True : 在结果中将组标签作为索引

sort = True : 结果是否按照分组关键字进行排序

dropna = True : 是否将NA看作普通键值用于分组,1.1版新增,False代表缺失值不删除

) # 生成的是分组索引标记,而不是新的DF

在数据分组之后,许多数据处理/分析/绘图命令都可以在各组间单独执行

df2g = df2.groupby('类型')
df2g
<pandas.core.groupby.generic.DataFrameGroupBy object at 0x000001E6C1C136A0>
df2g.groups
{'农林': [31, 45, 48, 64, 87, 94], '医药': [44, 69, 70, 72, 97], '师范': [14, 27, 33, 39, 49, 51, 71, 73, 85, 91, 95], '政法': [65], '民族': [88], '理工': [1, 8, 11, 12, 18, 19, 20, 24, 25, 28, 29, 30, 34, 36, 37, 38, 40, 41, 42, 43, 47, 50, 53, 54, 55, 56, 59, 60, 66, 67, 68, 77, 78, 80, 82, 83, 90, 92, 93], '综合': [0, 2, 3, 4, 5, 6, 7, 9, 10, 13, 15, 16, 17, 21, 22, 23, 26, 32, 35, 46, 52, 57, 58, 61, 62, 74, 79, 84, 86, 96, 98, 99], '财经': [63, 75, 76, 81, 89]}
df2g.describe()#把所有能描述的数值类型全部转换出来
名次总分...new2new3
countmeanstdmin25%50%75%maxcountmean...75%maxcountmeanstdmin25%50%75%max
类型
农林6.062.50000024.88975732.046.7557.082.2595.06.065.345000...8.1158798.2492426.08.0831040.1006137.9774688.0044728.0835838.1158798.249242
医药5.071.40000018.76965645.070.0071.073.0098.05.064.682000...8.0504668.1258855.08.0423330.0599757.9573878.0318128.0461178.0504668.125885
师范11.058.09090927.54071415.037.0052.080.0096.011.066.371818...8.1980568.64580811.08.1446060.2023067.9605288.0093528.1018528.1980568.645808
政法1.066.000000NaN66.066.0066.066.0066.01.064.900000...8.0560548.0560541.08.056054NaN8.0560548.0560548.0560548.0560548.056054
民族1.089.000000NaN89.089.0089.089.0089.01.063.780000...7.9862387.9862381.07.986238NaN7.9862387.9862387.9862387.9862387.986238
理工39.048.17948725.1802682.029.5042.067.5093.039.064.789231...8.2933709.92471739.08.2442490.3573177.9787228.0541918.1289618.2933709.924717
综合32.038.96875032.5878311.010.7525.562.25100.032.055.552812...8.72481410.00000032.08.4634120.4859677.9555018.0625688.3929798.72481410.000000
财经5.077.8000009.49736864.076.0077.082.0090.05.064.262000...8.0199758.0597775.08.0163190.0279837.9856127.9993758.0168578.0199758.059777

8 rows × 40 columns

df3g = df2.groupby(['类型', '所在省份'])
df3g.groups
{('农林', '北京'): [31, 87], ('农林', '广东'): [94], ('农林', '江苏'): [45], ('农林', '湖北'): [48], ('农林', '陕西'): [64], ('医药', '上海'): [70], ('医药', '北京'): [44, 97], ('医药', '重庆'): [69], ('医药', '陕西'): [72], ('师范', '上海'): [27], ('师范', '北京'): [14, 91], ('师范', '吉林'): [39], ('师范', '广东'): [73], ('师范', '江苏'): [49], ('师范', '浙江'): [95], ('师范', '湖北'): [33], ('师范', '湖南'): [71], ('师范', '重庆'): [51], ('师范', '陕西'): [85], ('政法', '北京'): [65], ('民族', '北京'): [88], ('理工', '上海'): [18, 47, 78], ('理工', '北京'): [1, 24, 29, 40, 41, 59, 67, 77, 82, 92], ('理工', '四川'): [36, 50], ('理工', '天津'): [19], ('理工', '安徽'): [11, 66], ('理工', '广东'): [30], ('理工', '江苏'): [43, 53, 55, 60, 80], ('理工', '河北'): [90], ('理工', '河南'): [54], ('理工', '浙江'): [93], ('理工', '湖北'): [12, 37, 38], ('理工', '湖南'): [8], ('理工', '福建'): [83], ('理工', '辽宁'): [25, 28], ('理工', '陕西'): [34, 42, 68], ('理工', '黑龙江'): [20, 56], ('综合', '上海'): [2, 6, 74], ('综合', '云南'): [58], ('综合', '北京'): [0, 5], ('综合', '吉林'): [10], ('综合', '四川'): [13], ('综合', '天津'): [15], ('综合', '安徽'): [96], ('综合', '山东'): [21, 52], ('综合', '山西'): [99], ('综合', '广东'): [9, 57, 86], ('综合', '广西'): [84], ('综合', '江苏'): [7, 23, 62, 98], ('综合', '江西'): [79], ('综合', '河南'): [61], ('综合', '浙江'): [4], ('综合', '湖北'): [3], ('综合', '湖南'): [17, 32], ('综合', '甘肃'): [35], ('综合', '福建'): [22], ('综合', '重庆'): [26], ('综合', '陕西'): [16, 46], ('财经', '上海'): [63], ('财经', '北京'): [81, 89], ('财经', '四川'): [76], ('财经', '湖北'): [75]}
df3g.sum() # 可以使用tab调用语法参考
名次总分consnew2new3
类型所在省份
农林北京120131.84216.23610716.236107
广东9563.6417.9774687.977468
江苏4665.9018.1178818.117881
湖北4965.7718.1098718.109871
陕西6564.9218.0572958.057295
.....................
综合陕西64139.44216.69336216.693362
财经上海6464.9618.0597778.059777
北京172127.76215.98498715.984987
四川7764.2718.0168578.016857
湖北7664.3218.0199758.019975

62 rows × 5 columns

dftmp = df2.copy()
dftmp.set_index(['类型','学校名称'],inplace =True)
dftmp
名次newvar总分所在省份所在城市办学方向主管部门consnew2new3cls
类型学校名称
综合北京大学1cons10.00北京北京市中国研究型教育部110.00000010.000000(0.999, 3.0]
理工清华大学2cons25.00北京北京市中国研究型教育部19.9247179.924717(0.999, 3.0]
综合复旦大学3cons10.00上海上海市中国研究型教育部19.0989019.098901(0.999, 3.0]
武汉大学4cons10.00湖北武汉市中国研究型教育部19.0790979.079097(3.0, 7.0]
浙江大学5cons10.00浙江杭州市中国研究型教育部19.0763439.076343(3.0, 7.0]
.......................................
师范浙江师范大学96cons63.37浙江金华市区域特色研究型浙江省17.9605287.960528NaN
综合安徽大学97cons63.34安徽合肥市区域研究型安徽省17.9586437.958643NaN
医药首都医科大学98cons63.32北京北京市区域特色研究型北京市17.9573877.957387NaN
综合江南大学99cons63.31江苏无锡市区域特色研究型教育部17.9567587.956758NaN
山西大学100cons63.29山西太原市区域研究型山西省17.9555017.955501NaN

100 rows × 11 columns

import numpy as np
dftmp.loc[('综合', '北京大学'), '办学方向'] = np.nan
dftmp
名次newvar总分所在省份所在城市办学方向主管部门consnew2new3cls
类型学校名称
综合北京大学1cons10.00北京北京市NaN教育部110.00000010.000000(0.999, 3.0]
理工清华大学2cons25.00北京北京市中国研究型教育部19.9247179.924717(0.999, 3.0]
综合复旦大学3cons10.00上海上海市中国研究型教育部19.0989019.098901(0.999, 3.0]
武汉大学4cons10.00湖北武汉市中国研究型教育部19.0790979.079097(3.0, 7.0]
浙江大学5cons10.00浙江杭州市中国研究型教育部19.0763439.076343(3.0, 7.0]
.......................................
师范浙江师范大学96cons63.37浙江金华市区域特色研究型浙江省17.9605287.960528NaN
综合安徽大学97cons63.34安徽合肥市区域研究型安徽省17.9586437.958643NaN
医药首都医科大学98cons63.32北京北京市区域特色研究型北京市17.9573877.957387NaN
综合江南大学99cons63.31江苏无锡市区域特色研究型教育部17.9567587.956758NaN
山西大学100cons63.29山西太原市区域研究型山西省17.9555017.955501NaN

100 rows × 11 columns

dftmp.groupby('办学方向', dropna = False).mean()
名次总分consnew2new3
办学方向
中国研究型18.58823558.0720591.08.6274768.627476
区域特色研究型86.53846263.9023081.07.9938017.993801
区域研究型74.43750064.4356251.08.0270388.027038
行业特色研究型58.11111165.3855561.08.0859328.085932
NaN1.00000010.0000001.010.00000010.000000
dftmp.groupby('办学方向', dropna = True).mean()
名次总分consnew2new3
办学方向
中国研究型18.58823558.0720591.08.6274768.627476
区域特色研究型86.53846263.9023081.07.9938017.993801
区域研究型74.43750064.4356251.08.0270388.027038
行业特色研究型58.11111165.3855561.08.0859328.085932

基于拆分进行筛选

筛选出出其中的一组

dfgroup.get_group()

df2g.get_group('农林').mean()
名次      62.500000
总分      65.345000
cons     1.000000
new2     8.083104
new3     8.083104
dtype: float64

筛选出所需的列

该操作也适用于希望对不同的变量列进行不同操作时

df2g['名次'].max()
类型
农林     95
医药     98
师范     96
政法     66
民族     89
理工     93
综合    100
财经     90
Name: 名次, dtype: int64

2.2分组汇总

在使用groupby完成数据拆分后,就可以按照需求分组进行信息汇总,此时可以使用其它专门的汇总命令,如agg来完成汇总操作

使用agg函数进行汇总

df.aggregate()

名称可以直接简写为agg,0.20版新增,可以用axis指定汇总维度

可以直接使用的汇总函数

count() Number of non-null observations

size() group sizes

sum() Sum of values

mean() Mean of values

median() Arithmetic median of values

min() Minimum

max() Maximum

std() Unbiased standard deviation

var() Unbiased variance

skew() Unbiased skewness (3rd moment)

kurt() Unbiased kurtosis (4th moment)

quantile() Sample quantile (value at %)

apply() Generic apply

cov() Unbiased covariance (binary)

corr() Correlation (binary)

df2g.agg('count')
名次newvar学校名称总分所在省份所在城市办学方向主管部门consnew2new3cls
类型
农林666666666660
医药555555555550
师范11111111111111111111110
政法111111111110
民族111111111110
理工39393939393939393939391
综合32323232323232323232326
财经555555555550
df2.agg('median')
名次      50.500000
总分      65.105000
cons     1.000000
new2     8.104937
new3     8.104937
dtype: float64
df2.agg(['mean', 'median'])
名次总分consnew2new3
mean50.4162.00031.08.2677988.267798
median50.5065.10501.08.1049378.104937
df2g.agg(['mean', 'median'])
名次总分consnew2new3
meanmedianmeanmedianmeanmedianmeanmedianmeanmedian
类型
农林62.50000057.065.34500065.345118.0831048.0835838.0831048.083583
医药71.40000071.064.68200064.740118.0423338.0461178.0423338.046117
师范58.09090952.066.37181865.640118.1446068.1018528.1446068.101852
政法66.00000066.064.90000064.900118.0560548.0560548.0560548.056054
民族89.00000089.063.78000063.780117.9862387.9862387.9862387.986238
理工48.17948742.064.78923165.670118.2442498.1289618.2442498.128961
综合38.96875025.555.55281265.060118.4634128.3929798.4634128.392979
财经77.80000077.064.26200064.270118.0163198.0168578.0163198.016857
# 引用非内置函数
import numpy as np
print(df2.总分.agg(np.sum))
df2g.总分.agg(np.sum)
6200.03

类型
农林     392.07
医药     323.41
师范     730.09
政法      64.90
民族      63.78
理工    2526.78
综合    1777.69
财经     321.31
Name: 总分, dtype: float64
# 引用自定义函数
def mymean(x):
    return x.mean()
df2.总分.agg(mymean)
62.00030000000001
df2g.agg(mymean)
名次总分consnew2new3
类型
农林62.50000065.34500018.0831048.083104
医药71.40000064.68200018.0423338.042333
师范58.09090966.37181818.1446068.144606
政法66.00000064.90000018.0560548.056054
民族89.00000063.78000017.9862387.986238
理工48.17948764.78923118.2442498.244249
综合38.96875055.55281218.4634128.463412
财经77.80000064.26200018.0163198.016319

named aggregation方式

0.25版新增,在汇总中同时指定列名和汇总函数,
从而能够在一个汇总命令中得到不同的汇总结果。#针对不同的变量进行不同的计算

df2g.agg(
    样本量 = pd.NamedAgg(column = '总分', aggfunc = 'count'),
    平均分 = pd.NamedAgg(column = '总分', aggfunc = np.mean),
    最低分 = pd.NamedAgg(column = '总分', aggfunc = 'min'),
    最高分 = pd.NamedAgg(column = '总分', aggfunc = 'max')
)
样本量平均分最低分最高分
类型
农林665.34500063.6468.05
医药564.68200063.3266.03
师范1166.37181863.3774.75
政法164.90000064.9064.90
民族163.78000063.7863.78
理工3964.78923125.0075.14
综合3255.55281210.0076.46
财经564.26200063.7764.96
df2g.agg(#可以简写
    样本量 = pd.NamedAgg('总分', 'count'),
    平均分 = pd.NamedAgg('总分', np.mean),
    最低分 = pd.NamedAgg('总分', 'min'),
    最高分 = pd.NamedAgg('总分', 'max')
)
样本量平均分最低分最高分
类型
农林665.34500063.6468.05
医药564.68200063.3266.03
师范1166.37181863.3774.75
政法164.90000064.9064.90
民族163.78000063.7863.78
理工3964.78923125.0075.14
综合3255.55281210.0076.46
财经564.26200063.7764.96

其他分组汇总方法

在生成交叉表的同时对单元格指定具体的汇总指标和汇总函数

df.pivot_table()
pd.crosstab()

pd.crosstab(df2.办学方向, df2.类型)#直接一步生成,不用先分组再汇总
类型农林医药师范政法民族理工综合财经
办学方向
中国研究型0030013190
区域特色研究型11500213
区域研究型002003110
行业特色研究型541112112

2.3重复测量数据的格式转换

基于多重索引,Pandas可以很容易地完成长型、宽型数据格式的相互转换。

转换为最简格式

df.stack(

level = -1 : 需要处理的索引级别(级别也是从0开始),默认为全部,int/string/list

dropna = True : 是否删除为缺失值的行

) # 转换后的结果可能为Series

df3 = pd.read_excel("儿童生长研究.xlsx", index_col= [0, 2])
df3
性别测量值
个体ID年龄
18F21.0
10F20.0
12F21.5
14F23.0
28F21.0
............
2614M30.0
278M22.0
10M21.5
12M23.5
14M25.0

108 rows × 2 columns

df3s = df3.stack()
df3s
个体ID  年龄     
1     8   性别        F
          测量值      21
      10  性别        F
          测量值      20
      12  性别        F
                 ... 
27    10  测量值    21.5
      12  性别        M
          测量值    23.5
      14  性别        M
          测量值      25
Length: 216, dtype: object

长宽型格式的自由互转(掌握下面两个即可)

df.unstack(

level = -1 : 需要处理的索引级别,默认为全部,int/string/list

fill_value : 用于填充缺失值的数值

)

df3s.unstack(1)#第一级索引即年龄,把年龄转换成列了
年龄8101214
个体ID
1性别FFFF
测量值212021.523
2性别FFFF
测量值2121.52425.5
3性别FFFF
..................
25测量值22.525.525.526
26性别MMMM
测量值2324.52630
27性别MMMM
测量值2221.523.525

54 rows × 4 columns

df3s.unstack([1,2])#2级索引即包含了性别和测量值的变量
年龄8101214
性别测量值性别测量值性别测量值性别测量值
个体ID
1F21F20F21.5F23
2F21F21.5F24F25.5
3F20.5F24F24.5F26
4F23.5F24.5F25F26.5
5F21.5F23F22.5F23.5
...........................
23M21.5M23.5M24M28
24M17M24.5M26M29.5
25M22.5M25.5M25.5M26
26M23M24.5M26M30
27M22M21.5M23.5M25

27 rows × 8 columns

数据转置

df.T

df3.T
个体ID123...252627
年龄81012148101214810...121481012148101214
性别FFFFFFFFFF...MMMMMMMMMM
测量值212021.5232121.52425.520.524...25.5262324.526302221.523.525

2 rows × 108 columns

其他可用于格式转换的命令(了解即可)

df.melt()
df.pivot()
df.pivot_table()

2.4多个数据源的合并

2.4.1数据的纵向合并(即合并行)

df.append(

other : 希望添加的DF/Series/字典/上述对象的列表(使用列表方式,就可以实现一次合并多个新对象)

ignore_index = False : 添加时是否忽略索引

verify_integrity = False : 是否检查索引值的唯一性,有重复时报错

)

df21 = pd.read_excel("高校信息.xlsx", sheet_name = 'part1')
df22 = pd.read_excel("高校信息.xlsx", sheet_name = 'part2')
df21 = df21.sort_values('总分')
df2 = df21.append(df22) # 注意索引值的大小
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门
4950南京师范大学65.71师范江苏南京市区域特色研究型江苏省
4849华中农业大学65.77农林湖北武汉市行业特色研究型教育部
4748华东理工大学65.79理工上海上海市行业特色研究型教育部
4647西北大学65.88综合陕西西安市区域研究型陕西省
4546南京农业大学65.90农林江苏南京市行业特色研究型教育部
...........................
4596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
4697安徽大学63.34综合安徽合肥市区域研究型安徽省
4798首都医科大学63.32医药北京北京市区域特色研究型北京市
4899江南大学63.31综合江苏无锡市区域特色研究型教育部
49100山西大学63.29综合山西太原市区域研究型山西省

100 rows × 8 columns

df2 = df21.append([df22, df22[:10], df22[40:]]) # 用list实现多个数据源的合并
df2
名次学校名称总分类型所在省份所在城市办学方向主管部门
4950南京师范大学65.71师范江苏南京市区域特色研究型江苏省
4849华中农业大学65.77农林湖北武汉市行业特色研究型教育部
4748华东理工大学65.79理工上海上海市行业特色研究型教育部
4647西北大学65.88综合陕西西安市区域研究型陕西省
4546南京农业大学65.90农林江苏南京市行业特色研究型教育部
...........................
4596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
4697安徽大学63.34综合安徽合肥市区域研究型安徽省
4798首都医科大学63.32医药北京北京市区域特色研究型北京市
4899江南大学63.31综合江苏无锡市区域特色研究型教育部
49100山西大学63.29综合山西太原市区域研究型山西省

120 rows × 8 columns

2.4.2数据的横向合并(合并列)

横向合并时

merge类sql 不给参数默认找共同列
concat属pandas 默认找索引(流水号除外),没有则按行位置直接拼接

merge命令使用类SQL的连接方式

pd.merge(

需要合并的DF

left : 需要合并的左侧DF
right : 需要合并的右侧DF
how = 'inner' : 具体的连接类型
{'left', 'right', 'outer', 'inner'}

两个DF的连接方式

on : 用于连接两个DF的关键变量(多个时为列表),必须在两侧都出现
left_on : 左侧DF用于连接的关键变量(多个时为列表)
right_on : 右侧DF用于连接的关键变量(多个时为列表)

left_index = False : 是否将左侧DF的索引用于连接
right_index = False : 是否将右侧DF的索引用于连接
其他附加设定
sort = False : 是否在合并前按照关键变量排序(会影响合并后的案例顺序)
suffixes : 重名变量的处理方式,提供长度为2的列表元素,分别作为后缀
suffixes=(‘_x’, ‘_y’)
copy = True
indicator = False : 在结果DF中增加’_merge’列,用于记录数据来源
也可以直接提供相应的变量列名
Categorical类型,取值:‘left_only’, ‘right_only’, ‘both’
validate = None : 核查合并类型是否为所指定的情况
‘one_to_one’ or ‘1:1’
‘one_to_many’ or ‘1:m’
‘many_to_one’ or ‘m:1’
‘many_to_many’ or ‘m:m’(实际上不做检查)
0.21版新增
)

df2a = pd.read_excel("高校信息.xlsx", sheet_name = 'var6')
df2b = pd.read_excel("高校信息.xlsx", sheet_name = 'var3')
pd.merge(df2a, df2b)
名次学校名称总分类型所在省份所在城市办学方向主管部门
01北京大学100.00综合北京北京市中国研究型教育部
12清华大学98.50理工北京北京市中国研究型教育部
23复旦大学82.79综合上海上海市中国研究型教育部
34武汉大学82.43综合湖北武汉市中国研究型教育部
45浙江大学82.38综合浙江杭州市中国研究型教育部
...........................
9596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
9697安徽大学63.34综合安徽合肥市区域研究型安徽省
9798首都医科大学63.32医药北京北京市区域特色研究型北京市
9899江南大学63.31综合江苏无锡市区域特色研究型教育部
99100山西大学63.29综合山西太原市区域研究型山西省

100 rows × 8 columns

pd.merge(df2a, df2b[:20])
名次学校名称总分类型所在省份所在城市办学方向主管部门
01北京大学100.00综合北京北京市中国研究型教育部
12清华大学98.50理工北京北京市中国研究型教育部
23复旦大学82.79综合上海上海市中国研究型教育部
34武汉大学82.43综合湖北武汉市中国研究型教育部
45浙江大学82.38综合浙江杭州市中国研究型教育部
...........................
1516南开大学74.46综合天津天津市中国研究型教育部
1617西安交通大学73.56综合陕西西安市中国研究型教育部
1718中南大学73.13综合湖南长沙市中国研究型教育部
1819同济大学72.85理工上海上海市中国研究型教育部
1920天津大学72.81理工天津天津市中国研究型教育部

20 rows × 8 columns

df2ai = df2a.set_index('学校名称')
df2bi = df2b.set_index('学校名称')
pd.merge(df2ai, df2bi, left_index = True, right_index = True)
名次总分类型所在省份所在城市办学方向主管部门
学校名称
北京大学1100.00综合北京北京市中国研究型教育部
清华大学298.50理工北京北京市中国研究型教育部
复旦大学382.79综合上海上海市中国研究型教育部
武汉大学482.43综合湖北武汉市中国研究型教育部
浙江大学582.38综合浙江杭州市中国研究型教育部
........................
浙江师范大学9663.37师范浙江金华市区域特色研究型浙江省
安徽大学9763.34综合安徽合肥市区域研究型安徽省
首都医科大学9863.32医药北京北京市区域特色研究型北京市
江南大学9963.31综合江苏无锡市区域特色研究型教育部
山西大学10063.29综合山西太原市区域研究型山西省

100 rows × 7 columns

df2ai = df2a.set_index('学校名称')
df2bi = df2b
pd.merge(df2ai, df2bi, left_index = True, right_on = '学校名称' )
名次总分类型所在省份所在城市学校名称办学方向主管部门
01100.00综合北京北京市北京大学中国研究型教育部
1298.50理工北京北京市清华大学中国研究型教育部
2382.79综合上海上海市复旦大学中国研究型教育部
3482.43综合湖北武汉市武汉大学中国研究型教育部
4582.38综合浙江杭州市浙江大学中国研究型教育部
...........................
959663.37师范浙江金华市浙江师范大学区域特色研究型浙江省
969763.34综合安徽合肥市安徽大学区域研究型安徽省
979863.32医药北京北京市首都医科大学区域特色研究型北京市
989963.31综合江苏无锡市江南大学区域特色研究型教育部
9910063.29综合山西太原市山西大学区域研究型山西省

100 rows × 8 columns

# 现在合并时索引名称和变量名称已经可以混用
pd.merge(df2ai, df2bi, on = '学校名称' )
学校名称名次总分类型所在省份所在城市办学方向主管部门
0北京大学1100.00综合北京北京市中国研究型教育部
1清华大学298.50理工北京北京市中国研究型教育部
2复旦大学382.79综合上海上海市中国研究型教育部
3武汉大学482.43综合湖北武汉市中国研究型教育部
4浙江大学582.38综合浙江杭州市中国研究型教育部
...........................
95浙江师范大学9663.37师范浙江金华市区域特色研究型浙江省
96安徽大学9763.34综合安徽合肥市区域研究型安徽省
97首都医科大学9863.32医药北京北京市区域特色研究型北京市
98江南大学9963.31综合江苏无锡市区域特色研究型教育部
99山西大学10063.29综合山西太原市区域研究型山西省

100 rows × 8 columns

Concat命令简介

同时支持横向合并与纵向合并

pd.concat(
objs : 需要合并的对象,列表形式提供
axis = 0 : 对行还是对列方向进行合并
{0/‘index’, 1/‘columns’}
join = ‘outer’ : 对另一个轴向的索引值如何进行处理
{‘inner’, ‘outer’}
ignore_index = False
keys = None : 为不同数据源的提供合并后的索引值
verify_integrity = False
copy = True
)

# 纵向合并
df21 = pd.read_excel("高校信息.xlsx", sheet_name = 'part1')
df22 = pd.read_excel("高校信息.xlsx", sheet_name = 'part2')
pd.concat([df21, df22])
名次学校名称总分类型所在省份所在城市办学方向主管部门
01北京大学100.00综合北京北京市中国研究型教育部
12清华大学98.50理工北京北京市中国研究型教育部
23复旦大学82.79综合上海上海市中国研究型教育部
34武汉大学82.43综合湖北武汉市中国研究型教育部
45浙江大学82.38综合浙江杭州市中国研究型教育部
...........................
4596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
4697安徽大学63.34综合安徽合肥市区域研究型安徽省
4798首都医科大学63.32医药北京北京市区域特色研究型北京市
4899江南大学63.31综合江苏无锡市区域特色研究型教育部
49100山西大学63.29综合山西太原市区域研究型山西省

100 rows × 8 columns

pd.concat([df21, df22], keys = ['A', 'B'])
名次学校名称总分类型所在省份所在城市办学方向主管部门
A01北京大学100.00综合北京北京市中国研究型教育部
12清华大学98.50理工北京北京市中国研究型教育部
23复旦大学82.79综合上海上海市中国研究型教育部
34武汉大学82.43综合湖北武汉市中国研究型教育部
45浙江大学82.38综合浙江杭州市中国研究型教育部
..............................
B4596浙江师范大学63.37师范浙江金华市区域特色研究型浙江省
4697安徽大学63.34综合安徽合肥市区域研究型安徽省
4798首都医科大学63.32医药北京北京市区域特色研究型北京市
4899江南大学63.31综合江苏无锡市区域特色研究型教育部
49100山西大学63.29综合山西太原市区域研究型山西省

100 rows × 8 columns

# 横向合并
df2a = pd.read_excel("高校信息.xlsx", sheet_name = 'var6')
df2b = pd.read_excel("高校信息.xlsx", sheet_name = 'var3')
pd.concat([df2a, df2b], axis = 1)#因为没有索引,所以直接按行位置合并
名次学校名称总分类型所在省份所在城市学校名称办学方向主管部门
01北京大学100.00综合北京北京市北京大学中国研究型教育部
12清华大学98.50理工北京北京市清华大学中国研究型教育部
23复旦大学82.79综合上海上海市复旦大学中国研究型教育部
34武汉大学82.43综合湖北武汉市武汉大学中国研究型教育部
45浙江大学82.38综合浙江杭州市浙江大学中国研究型教育部
..............................
9596浙江师范大学63.37师范浙江金华市浙江师范大学区域特色研究型浙江省
9697安徽大学63.34综合安徽合肥市安徽大学区域研究型安徽省
9798首都医科大学63.32医药北京北京市首都医科大学区域特色研究型北京市
9899江南大学63.31综合江苏无锡市江南大学区域特色研究型教育部
99100山西大学63.29综合山西太原市山西大学区域研究型山西省

100 rows × 9 columns

df2ai = df2a.set_index('学校名称')
df2bi = df2b.set_index('学校名称')
pd.concat([df2ai, df2bi], axis = 1)
名次总分类型所在省份所在城市办学方向主管部门
学校名称
北京大学1100.00综合北京北京市中国研究型教育部
清华大学298.50理工北京北京市中国研究型教育部
复旦大学382.79综合上海上海市中国研究型教育部
武汉大学482.43综合湖北武汉市中国研究型教育部
浙江大学582.38综合浙江杭州市中国研究型教育部
........................
浙江师范大学9663.37师范浙江金华市区域特色研究型浙江省
安徽大学9763.34综合安徽合肥市区域研究型安徽省
首都医科大学9863.32医药北京北京市区域特色研究型北京市
江南大学9963.31综合江苏无锡市区域特色研究型教育部
山西大学10063.29综合山西太原市区域研究型山西省

100 rows × 7 columns

实战:对PM2.5数据做基本整理

  bj2012
SiteParameterDate (LST)YearMonthDayHourValueUnitDurationQC Namehighhigh2high3
0BeijingPM2.52012-1-1 0:002012110303礸/mg?1 HrValid1.02(298.2, 318.08]
1BeijingPM2.52012-1-1 1:002012111215礸/mg?1 HrValid1.02(198.8, 218.68]
2BeijingPM2.52012-1-1 2:002012112222礸/mg?1 HrValid1.02(218.68, 238.56]
3BeijingPM2.52012-1-1 3:00201211385礸/mg?1 HrValid0.00(79.52, 99.4]
4BeijingPM2.52012-1-1 4:00201211438礸/mg?1 HrValid0.00(19.88, 39.76]
.............................................
8779BeijingPM2.52012-12-31 19:002012123119131礸/mg?1 HrValidNaN0.01(119.28, 139.16]
8780BeijingPM2.52012-12-31 20:002012123120113礸/mg?1 HrValidNaN0.01(99.4, 119.28]
8781BeijingPM2.52012-12-31 21:00201212312145礸/mg?1 HrValidNaN0.00(39.76, 59.64]
8782BeijingPM2.52012-12-31 22:00201212312239礸/mg?1 HrValidNaN0.00(19.88, 39.76]
8783BeijingPM2.52012-12-31 23:00201212312335礸/mg?1 HrValidNaN0.00(19.88, 39.76]

8295 rows × 14 columns

bj2012g= bj2012.groupby('Month')
bj2012g['Value'].mean()
Month
1     118.922388
2      84.442029
3      96.474324
4      87.835883
5      90.966715
         ...    
8      81.165329
9      59.784314
10     94.951351
11     87.436963
12    109.187296
Name: Value, Length: 12, dtype: float64
bj2012[bj2012.Value>200].Day.nunique()#nuique计算非重复数值的个数
31
bj2012[bj2012.Value>300].Day.nunique()
23
bj2012[bj2012.Value>500].Day.nunique()
3
bj2009x = pd.read_csv("PM25\Beijing_2012_HourlyPM2.5_created20140325 - 2009.csv",encoding ="gbk",skiprows=3,index_col='Year')#注意sep
bj2009x
SiteParameterDate (LST)MonthDayHourValueUnitDurationQC Name
Year
2009BeijingPM2.52009-1-1 0:00110-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 1:00111-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 2:00112-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 3:00113-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 4:00114-999礸/m?1 HrMissingNaN
.................................
2009BeijingPM2.52009-12-31 19:0012311977礸/m?1 HrValidNaN
2009BeijingPM2.52009-12-31 20:00123120120礸/m?1 HrValidNaN
2009BeijingPM2.52009-12-31 21:00123121163礸/m?1 HrValidNaN
2009BeijingPM2.52009-12-31 22:00123122167礸/m?1 HrValidNaN
2009BeijingPM2.52009-12-31 23:00123123-999礸/m?1 HrMissingNaN

8760 rows × 10 columns

bj2012x=bj2012.set_index('Year')
bj2012x
SiteParameterDate (LST)MonthDayHourValueUnitDurationQC Name
Year
2012BeijingPM2.52012-1-1 0:00110303礸/mg?1 HrValid
2012BeijingPM2.52012-1-1 1:00111215礸/mg?1 HrValid
2012BeijingPM2.52012-1-1 2:00112222礸/mg?1 HrValid
2012BeijingPM2.52012-1-1 3:0011385礸/mg?1 HrValid
2012BeijingPM2.52012-1-1 4:0011438礸/mg?1 HrValid
.................................
2012BeijingPM2.52012-12-31 19:00123119131礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 20:00123120113礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 21:0012312145礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 22:0012312239礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 23:0012312335礸/mg?1 HrValidNaN

8784 rows × 10 columns

bj2009_2012=pd.concat([bj2009x, bj2012x])
bj2009_2012
SiteParameterDate (LST)MonthDayHourValueUnitDurationQC Name
Year
2009BeijingPM2.52009-1-1 0:00110-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 1:00111-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 2:00112-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 3:00113-999礸/m?1 HrMissingNaN
2009BeijingPM2.52009-1-1 4:00114-999礸/m?1 HrMissingNaN
.................................
2012BeijingPM2.52012-12-31 19:00123119131礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 20:00123120113礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 21:0012312145礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 22:0012312239礸/mg?1 HrValidNaN
2012BeijingPM2.52012-12-31 23:0012312335礸/mg?1 HrValidNaN

17544 rows × 10 columns

bj2009_2012x=bj2009_2012.stack()
bj2009_2012x
Year            
2009  Site                Beijing
      Parameter             PM2.5
      Date (LST)    2009-1-1 0:00
      Month                     1
      Day                       1
                        ...      
2012  Day                      31
      Hour                     23
      Value                    35
      Unit              礸/mg?1 Hr
      Duration              Valid
Length: 158005, dtype: object
  • 6
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值