Python 数据分析 Pandas

1 Pandas基本介绍

Python Data Analysis Library或pandas是基于Numpy的一种工具,该工具是为了解决数据分析任务而创建的。Pandas纳入了大量库和一些标准的数据模型,提供了高效地操作大型数据集所Pandas操作需要的工具。pandas提供了大量能使我们快速便捷的处理数据的函数和方法。

本篇文章需要的数据集:https://files.cnblogs.com/files/wkfvawl/豆瓣电影数据xlsx.zip
注意:需要数据集扩展名改为xlsx才能使用!

import pandas as pd
import numpy as np

1.1 Pandas的基本数据结构

pandas中有两种常用的基本结构

•Series

一维数组,与Numpy中的一维array类似,二者与Python基本的数据结构List也很相似。Series能保存不同种数据类型,字符串、boolean值、数字等都能保存在Series种。

•DataFrame

二维的表格型数据结构,很多功能与R中的data.frame类似。可以将DataFrame理解为Series的容器

1.1.1 Pandas库的Series类型

一维Series可以用一维列表初始化

s=pd.Series([1,3,5,np.nan,6,5])
print(s)
0    1.0
1    3.0
2    5.0
3    NaN
4    6.0
5    5.0
dtype: float64

默认的情况下,Series的下标都是数字(可以使用额外参数指定),类型是统一的。

b=pd.Series([1,3,5,np.nan,6,5],index=['a','b','c','d','e','f'])
print(b)
a    1.0
b    3.0
c    5.0
d    NaN
e    6.0
f    5.0
dtype: float64

索引——数据行标签

s.index
RangeIndex(start=0, stop=6, step=1)
b.index
Index(['a', 'b', 'c', 'd', 'e', 'f'], dtype='object')

取值

s.values
array([ 1.,  3.,  5., nan,  6.,  5.])
s[4]
6.0

切片操作

s[2:5]
2    5.03    NaN4    6.0dtype: float64
s[::2]
0    1.02    5.04    6.0dtype: float64
b['b':'f':2]
b    3.0d    NaNf    5.0dtype: float64

索引赋值

s.index.name='索引's
索引0    1.01    3.02    5.03    NaN4    6.05    5.0dtype: float64
s.index=list('abcdef')s
a    1.0b    3.0c    5.0d    NaNe    6.0f    5.0dtype: float64
s['a':'c'] #注意这里不是左闭右开 左右都是闭区间
a    1.0b    3.0c    5.0dtype: float64

1.1.2 Pandas库的DataFrame类型

DataFrame初始化

DataFrame是个二维结构,这里首先构造一组时间序列,作为第一维的下标

date=pd.date_range('20200101',periods=6)#起点20200101 6个日期print(date)
DatetimeIndex(['2020-01-01', '2020-01-02', '2020-01-03', '2020-01-04',               '2020-01-05', '2020-01-06'],              dtype='datetime64[ns]', freq='D')

然后创建一个DataFream结构 传入一个二维数组 6行4列

df=pd.DataFrame(np.random.randn(6,4))
df    #默认使用0、1、2.。。作为索引index
0 1 2 3
0 -1.490125 1.298987 -0.543361 1.221980
1 -0.849709 0.118608 -0.955715 0.144980
2 -0.599598 -0.756037 -1.795249 -0.282495
3 -0.332586 1.750622 -1.493345 -2.100013
4 -0.905893 -0.254791 -1.476728 -0.001651
5 -1.121065 -1.861881 -0.502420 0.523135
df=pd.DataFrame(np.random.randn(6,4),index=date,columns=list('ABCD'))
df    #index参数设置行索引,columns参数设置列索引
A B C D
2020-01-01 -0.632187 1.388384 -1.141516 0.555858
2020-01-02 -1.033370 0.220262 -0.348647 -1.784751
2020-01-03 2.162017 -0.374234 -0.636569 0.490510
2020-01-04 0.392639 -0.329270 -1.017615 0.153913
2020-01-05 -1.302436 0.436321 -0.186632 -0.179940
2020-01-06 -1.105173 0.068276 -1.644065 0.815162

除了向DataFrame中传入二维数组,我们也可以使用字典传入数据

df1=pd.DataFrame({'A':1,'B':pd.Timestamp('20200101'),'C':pd.Series(1,index=list(range(4)),dtype=float),'D':np.array([3]*4,dtype=int),'E':pd.Categorical(['test','train','test','train']),'F':'abc'})
df1
A B C D E F
0 1 2020-01-01 1.0 3 test abc
1 1 2020-01-01 1.0 3 train abc
2 1 2020-01-01 1.0 3 test abc
3 1 2020-01-01 1.0 3 train abc

字典的每个key代表一列,其value可以是各种能够转化为Series的对象

与Series要求所有的类型都一致不同,DataFrame只要求每一列数据的格式相同

df1.dtypes
A             int64B    datetime64[ns]C           float64D             int32E          categoryF            objectdtype: object
DataFrame查看数据

头尾数据

head和tail方法可以分别查看最前面几行和最后面几行的数据(默认为5)

df.head()
A B C D
2020-01-01 -0.632187 1.388384 -1.141516 0.555858
2020-01-02 -1.033370 0.220262 -0.348647 -1.784751
2020-01-03 2.162017 -0.374234 -0.636569 0.490510
2020-01-04 0.392639 -0.329270 -1.017615 0.153913
2020-01-05 -1.302436 0.436321 -0.186632 -0.179940
df.tail(3)  #看最后三行
A B C D
2020-01-04 0.392639 -0.329270 -1.017615 0.153913
2020-01-05 -1.302436 0.436321 -0.186632 -0.179940
2020-01-06 -1.105173 0.068276 -1.644065 0.815162

下标、列标、数据

下标使用index属性查看

df.index
DatetimeIndex(['2020-01-01', '2020-01-02', '2020-01-03', '2020-01-04',               '2020-01-05', '2020-01-06'],              dtype='datetime64[ns]', freq='D')

列标使用columns属性查看

df.columns
Index(['A', 'B', 'C', 'D'], dtype='object')

数据值使用values查看

df.values
array([[ 0.44397794, -0.56828038,  0.53942245, -1.8088147 ],       [-0.94194603,  1.60065473, -0.16541752, -0.14333282],       [ 0.05818642,  1.2996908 , -0.72258188, -0.25816996],       [ 0.91244089, -1.34726583, -0.82709665, -1.18962492],       [ 0.42712501,  0.01041125, -0.39041139,  1.17227685],       [-0.58428589, -0.42811927,  0.53630517,  1.32747977]])

1.2 Pandas读取数据及数据操作

我们以豆瓣的电影数据作为我们深入了解Pandas的示例

df_mv=pd.read_excel(r'豆瓣电影数据.xlsx') #加 r 防止转义df_mv.head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2 美丽人生 327855.0 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港

1.2.1 行操作

df_mv.iloc[0] #第一行
Unnamed: 0                      1名字                           控方证人投票人数                        42995类型                       剧情/悬疑/犯罪产地                             美国上映时间          1957-12-17 00:00:00时长                            116年代                           1957评分                            9.5首映地点                           美国Name: 1, dtype: object
df_mv.iloc[0:5] #前五行
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2 美丽人生 327855.0 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港

也可以使用 loc

df_mv.loc[0:5]
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2 美丽人生 327855.0 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港
5 5 泰坦尼克号 157074.0 剧情/爱情/灾难 美国 2012-04-10 00:00:00 194 2012 9.4 中国大陆
添加一行
dit={'名字':'复仇者联盟3',     '投票人数':123456,     '类型':'剧情/科幻',     '产地':'美国',     '上映时间':'2017-05-04 00:00:00',     '时长':142,     '年代':2017,     '评分':8.7,     '首映地点':'美国'}
s=pd.Series(dit)s.name=38738 #名称 索引号s
名字                   复仇者联盟3投票人数                 123456类型                    剧情/科幻产地                       美国上映时间    2017-05-04 00:00:00时长                      142年代                     2017评分                      8.7首映地点                     美国Name: 38738, dtype: object
df_mv=df_mv.append(s) #append添加df_mv.tail()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
38734 38734.0 1935年 57.0 喜剧/歌舞 美国 1935-03-15 00:00:00 98 1935 7.6 美国
38735 38735.0 血溅画屏 95.0 剧情/悬疑/犯罪/武侠/古装 中国大陆 1905-06-08 00:00:00 91 1986 7.1 美国
38736 38736.0 魔窟中的幻想 51.0 惊悚/恐怖/儿童 中国大陆 1905-06-08 00:00:00 78 1986 8.0 美国
38737 38737.0 列宁格勒围困之星火战役 Блокада: Фильм 2: Ленинградский ме... 32.0 剧情/战争 苏联 1905-05-30 00:00:00 97 1977 6.6 美国
38738 NaN 复仇者联盟3 123456.0 剧情/科幻 美国 2017-05-04 00:00:00 142 2017 8.7 美国
删除一行
df_mv=df_mv.drop([38738])
df_mv.tail()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
38733 38733.0 神学院 S 46.0 Adult 法国 1905-06-05 00:00:00 58 1983 8.6 美国
38734 38734.0 1935年 57.0 喜剧/歌舞 美国 1935-03-15 00:00:00 98 1935 7.6 美国
38735 38735.0 血溅画屏 95.0 剧情/悬疑/犯罪/武侠/古装 中国大陆 1905-06-08 00:00:00 91 1986 7.1 美国
38736 38736.0 魔窟中的幻想 51.0 惊悚/恐怖/儿童 中国大陆 1905-06-08 00:00:00 78 1986 8.0 美国
38737 38737.0 列宁格勒围困之星火战役 Блокада: Фильм 2: Ленинградский ме... 32.0 剧情/战争 苏联 1905-05-30 00:00:00 97 1977 6.6 美国

1.2.2 列操作

df_mv.columns
Index(['Unnamed: 0', '名字', '投票人数', '类型', '产地', '上映时间', '时长', '年代', '评分',       '首映地点'],      dtype='object')
df_mv['名字'][0:5] #名字列的前五行
0    肖申克的救赎1      控方证人2     美丽人生 3      阿甘正传4      霸王别姬Name: 名字, dtype: object
df_mv[['名字','类型']][:5] #取多列 采用list的形式
名字 类型
0 肖申克的救赎 剧情/犯罪
1 控方证人 剧情/悬疑/犯罪
2 美丽人生 剧情/喜剧/爱情
3 阿甘正传 剧情/爱情
4 霸王别姬 剧情/爱情/同性
增加一列
df_mv['序号']=range(1,len(df_mv)+1)#左闭右开df_mv.head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点 序号
0 0.0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节 1
1 1.0 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国 2
2 2.0 美丽人生 327855.0 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利 3
3 3.0 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映 4
4 4.0 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港 5
删除一列
df_mv=df_mv.drop('序号',axis=1) #axis=0 表示行 默认 axis=1 表示列df_mv.head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1.0 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2.0 美丽人生 327855.0 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3.0 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4.0 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港

1.2.3 通过标签选择数据

df.loc[[index],[column]]通过标签选择数据

df_mv.loc[[1,3,5,7,9],['名字','评分']]
名字 评分
1 控方证人 9.5
3 阿甘正传 9.4
5 泰坦尼克号 9.4
7 新世纪福音战士剧场版:Air/真心为你 新世紀エヴァンゲリオン劇場版 Ai 9.4
9 这个杀手不太冷 9.4
df_mv.loc[1,'名字']
'控方证人'
条件选择

选取产地为美国的所有电音

df_mv[df_mv['产地']=='美国']#布尔型取数
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1.0 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
3 3.0 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
5 5.0 泰坦尼克号 157074.0 剧情/爱情/灾难 美国 2012-04-10 00:00:00 194 2012 9.4 中国大陆
6 6.0 辛德勒的名单 306904.0 剧情/历史/战争 美国 1993-11-30 00:00:00 195 1993 9.4 华盛顿首映
... ... ... ... ... ... ... ... ... ... ...
38724 38724.0 跷家的一夜 82.0 喜剧/动作/惊悚/冒险 美国 1987-07-01 00:00:00 102 1987 7.8 美国
38726 38726.0 零下的激情 199.0 剧情/爱情/犯罪 美国 1987-11-06 00:00:00 98 1987 7.4 美国
38728 38728.0 离别秋波 240.0 剧情/爱情/音乐 美国 1986-02-19 00:00:00 90 1986 8.2 美国
38732 38732.0 极乐森林 45.0 纪录片 美国 1986-09-14 00:00:00 90 1986 8.1 美国
38734 38734.0 1935年 57.0 喜剧/歌舞 美国 1935-03-15 00:00:00 98 1935 7.6 美国

11866 rows × 10 columns

df_mv[df_mv['产地']=='中国大陆'][:5] # 前5行
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
4 4.0 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港
21 21.0 大闹天宫 74881.0 动画/奇幻 中国大陆 1905-05-14 00:00:00 114 1961 9.2 上集
29 29.0 穹顶之下 51113.0 纪录片 中国大陆 2015-02-28 00:00:00 104 2015 9.2 中国大陆
38 38.0 茶馆 10678.0 剧情/历史 中国大陆 1905-06-04 00:00:00 118 1982 9.2 美国
45 45.0 山水情 10781.0 动画/短片 中国大陆 1905-06-10 00:00:00 19 1988 9.2 美国

选取产地为美国,且评分大于9的电影

df_mv[(df_mv.产地=='美国')&(df_mv.评分>9)].head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1.0 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
3 3.0 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
5 5.0 泰坦尼克号 157074.0 剧情/爱情/灾难 美国 2012-04-10 00:00:00 194 2012 9.4 中国大陆
6 6.0 辛德勒的名单 306904.0 剧情/历史/战争 美国 1993-11-30 00:00:00 195 1993 9.4 华盛顿首映

选取产地为美国或中国大陆,且评分大于9的电影

df_mv[((df_mv.产地=='美国')|(df_mv.产地=='中国大陆'))&(df_mv.评分>9)].head()#用括号划分逻辑
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795.0 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1.0 控方证人 42995.0 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
3 3.0 阿甘正传 580897.0 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4.0 霸王别姬 478523.0 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港
5 5.0 泰坦尼克号 157074.0 剧情/爱情/灾难 美国 2012-04-10 00:00:00 194 2012 9.4 中国大陆

1.3 数据清洗

1.3.1 缺失值处理

dropna:根据标签中的缺失值进行过滤,删除缺失值

fillna:对缺失值进行填充

isnull:返回一个布尔值对象,判断哪些值是缺失值

notnull:isnull的否定式

判断缺失值

isnull

# 所有电影名称缺失的df_mv[df_mv['名字'].isnull()].head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
231 231.0 NaN 144.0 纪录片/音乐 韩国 2011-02-02 00:00:00 90 2011 9.7 美国
361 361.0 NaN 80.0 短片 其他 1905-05-17 00:00:00 4 1964 5.7 美国
369 369.0 NaN 5315.0 剧情 日本 2004-07-10 00:00:00 111 2004 7.5 日本
372 372.0 NaN 263.0 短片/音乐 英国 1998-06-30 00:00:00 34 1998 9.2 美国
374 374.0 NaN 47.0 短片 其他 1905-05-17 00:00:00 3 1964 6.7 美国
填充缺失值

填充字符类

df_mv['名字'].fillna('未知电影',inplace=True) #用'未知电影'填充没有名字的电影
df_mv[df_mv['名字']=='未知电影'].head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
231 231.0 未知电影 144.0 纪录片/音乐 韩国 2011-02-02 00:00:00 90 2011 9.7 美国
361 361.0 未知电影 80.0 短片 其他 1905-05-17 00:00:00 4 1964 5.7 美国
369 369.0 未知电影 5315.0 剧情 日本 2004-07-10 00:00:00 111 2004 7.5 日本
372 372.0 未知电影 263.0 短片/音乐 英国 1998-06-30 00:00:00 34 1998 9.2 美国
374 374.0 未知电影 47.0 短片 其他 1905-05-17 00:00:00 3 1964 6.7 美国

填充数值类

##添加一行,用于实验。此处设置评分为空nandit={'名字':'复仇者联盟3',     '投票人数':123456,     '类型':'剧情/科幻',     '产地':'美国',     '上映时间':'2017-05-04 00:00:00',     '时长':142,     '年代':2017,     '评分':np.nan,     '首映地点':'美国'}s=pd.Series(dit)s.name=38738df_mv=df_mv.append(s)
##判断“评分”为空的df_mv[df_mv['评分'].isnull()].head()
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
38738 NaN 复仇者联盟3 123456.0 剧情/科幻 美国 2017-05-04 00:00:00 142 2017 NaN 美国
##填充评分,此处填充 均值df_mv['评分'].fillna(np.mean(df_mv['评分']),inplace=True)df_mv[-1:]
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
38738 NaN 复仇者联盟3 123456.0 剧情/科幻 美国 2017-05-04 00:00:00 142 2017 6.935704 美国
删除缺失值

df.dropna(参数)


subset=['列名']:删除该列为空的行

how='all':删除全为空值的行或列

inplace=True:覆盖之前的数据

axis=0:选择行或列(=0,删除一行;=1,删除一列),默认为0

len(df_mv)
38739
df_mv1=df_mv.dropna()
len(df_mv1)
38735

1.3.2 异常值处理

异常值,即在数据集中存在不合理的值,又称离群点。比如年龄为-1,笔记本电脑重量为1吨等等,都属与异常值的范围。

对于异常值,一般来说数量都会很少,在不影响整体数据分布的情况下,我们直接删除就可以了。

df_mv[(df_mv.投票人数<0)|(df_mv['投票人数']%1!=0)]
Unnamed: 0 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
19777 19777.0 皇家大贼 皇家大 -80.00 剧情/犯罪 中国香港 1985-05-31 00:00:00 60 1985 6.3 美国
19786 19786.0 日本的垃圾去中国大陆 にっぽんの“ゴミ” 大陆へ渡る ~中国式リサイクル錬 -80.00 纪录片 日本 1905-06-26 00:00:00 60 2004 7.9 美国
19791 19791.0 女教师 女教 8.30 剧情/犯罪 日本 1977-10-29 00:00:00 100 1977 6.6 日本
19797 19797.0 女教徒 -118.00 剧情 法国 1966-05-06 00:00:00 135 1966 7.8 美国
19804 19804.0 女郎漫游仙境 ドレミファ娘の血は騒 5.90 喜剧/歌舞 日本 1985-11-03 00:00:00 80 1985 6.7 日本
19820 19820.0 女仆日记 12.87 剧情 法国 2015-04-01 00:00:00 96 2015 5.7 法国
38055 38055.0 逃出亚卡拉 12.87 剧情/动作/惊悚/犯罪 美国 1979-09-20 00:00:00 112 1979 7.8 美国
df_mv=df_mv[df_mv.投票人数>0]
df_mv=df_mv[df_mv['投票人数']%1==0]

1.4 数据保存

数据处理之后,然后将数据重新保存到原文件

df_mv.to_excel('movie_data.xlsx')

2 Pandas操作

import pandas as pdimport numpy as np

以豆瓣电影为例

df=pd.read_excel('movie_data.xlsx')
df=df.drop('Unnamed: 0',axis=1)
df.head()
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1.0 控方证人 42995 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2.0 美丽人生 327855 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3.0 阿甘正传 580897 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4.0 霸王别姬 478523 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港

2.1 数据格式转换

在做数据分析的时候,原始数据往往会因为各种各样的原因 产生各种数据格式的问题。

数据格式是我们非常需要注意的一点,数据格式错误往往会造成很严重的后果。

并且,很多异常值也是我们经过格式转换之后才会发现,对我们规整数据,清洗数据有很重要的作用。

查看格式

df['投票人数'].dtype
dtype('int64')

格式转化

df['投票人数']=df['投票人数'].astype('int')
df['投票人数'].dtype
dtype('int32')

将年代格式转化为整型

df['年代'].dtype
dtype('O')
df['年代']=df['年代'].astype('int')
---------------------------------------------------------------------------ValueError                                Traceback (most recent call last)<ipython-input-8-7db608df647a> in <module>----> 1 df['年代']=df['年代'].astype('int')


D:\anaconda\lib\site-packages\pandas\core\generic.py in astype(self, dtype, copy, errors)   5696         else:   5697             # else, only a single dtype is given-> 5698             new_data = self._data.astype(dtype=dtype, copy=copy, errors=errors)   5699             return self._constructor(new_data).__finalize__(self)   5700 


D:\anaconda\lib\site-packages\pandas\core\internals\managers.py in astype(self, dtype, copy, errors)    580     581     def astype(self, dtype, copy: bool = False, errors: str = "raise"):--> 582         return self.apply("astype", dtype=dtype, copy=copy, errors=errors)    583     584     def convert(self, **kwargs):


D:\anaconda\lib\site-packages\pandas\core\internals\managers.py in apply(self, f, filter, **kwargs)    440                 applied = b.apply(f, **kwargs)    441             else:--> 442                 applied = getattr(b, f)(**kwargs)    443             result_blocks = _extend_blocks(applied, result_blocks)    444 


D:\anaconda\lib\site-packages\pandas\core\internals\blocks.py in astype(self, dtype, copy, errors)    623             vals1d = values.ravel()    624             try:--> 625                 values = astype_nansafe(vals1d, dtype, copy=True)    626             except (ValueError, TypeError):    627                 # e.g. astype_nansafe can fail on object-dtype of strings


D:\anaconda\lib\site-packages\pandas\core\dtypes\cast.py in astype_nansafe(arr, dtype, copy, skipna)    872         # work around NumPy brokenness, #1987    873         if np.issubdtype(dtype.type, np.integer):--> 874             return lib.astype_intsafe(arr.ravel(), dtype).reshape(arr.shape)    875     876         # if we have a datetime/timedelta array of objects


pandas\_libs\lib.pyx in pandas._libs.lib.astype_intsafe()


ValueError: invalid literal for int() with base 10: '2008\u200e'

通过条件判断找到异常数据

##年代中有异常值 '2008\u200e',无法正常转化df[df.年代=='2008\u200e']
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
15205 15205.0 狂蟒惊魂 544 恐怖 中国大陆 2008-04-08 00:00:00 93 2008‎ 2.7 美国
df[df.年代=='2008\u200e']['年代'].values
array(['2008\u200e'], dtype=object)
带有Unicode的格式控制字符,从左到右的书写标记
df.loc[15205,'年代']=2008df.loc[15205]
Unnamed: 0.1                  15205名字                             狂蟒惊魂投票人数                            544类型                               恐怖产地                             中国大陆上映时间            2008-04-08 00:00:00时长                               93年代                             2008评分                              2.7首映地点                             美国Name: 15205, dtype: object
df['年代']=df['年代'].astype('int')df['年代'][:5]
0    19941    19572    19973    19944    1993Name: 年代, dtype: int32

将时长转化为整数格式

df['时长']=df['时长'].astype('int')
---------------------------------------------------------------------------ValueError                                Traceback (most recent call last)<ipython-input-15-83bf9b6fa2b3> in <module>----> 1 df['时长']=df['时长'].astype('int')


D:\anaconda\lib\site-packages\pandas\core\generic.py in astype(self, dtype, copy, errors)   5696         else:   5697             # else, only a single dtype is given-> 5698             new_data = self._data.astype(dtype=dtype, copy=copy, errors=errors)   5699             return self._constructor(new_data).__finalize__(self)   5700 


D:\anaconda\lib\site-packages\pandas\core\internals\managers.py in astype(self, dtype, copy, errors)    580     581     def astype(self, dtype, copy: bool = False, errors: str = "raise"):--> 582         return self.apply("astype", dtype=dtype, copy=copy, errors=errors)    583     584     def convert(self, **kwargs):


D:\anaconda\lib\site-packages\pandas\core\internals\managers.py in apply(self, f, filter, **kwargs)    440                 applied = b.apply(f, **kwargs)    441             else:--> 442                 applied = getattr(b, f)(**kwargs)    443             result_blocks = _extend_blocks(applied, result_blocks)    444 


D:\anaconda\lib\site-packages\pandas\core\internals\blocks.py in astype(self, dtype, copy, errors)    623             vals1d = values.ravel()    624             try:--> 625                 values = astype_nansafe(vals1d, dtype, copy=True)    626             except (ValueError, TypeError):    627                 # e.g. astype_nansafe can fail on object-dtype of strings


D:\anaconda\lib\site-packages\pandas\core\dtypes\cast.py in astype_nansafe(arr, dtype, copy, skipna)    872         # work around NumPy brokenness, #1987    873         if np.issubdtype(dtype.type, np.integer):--> 874             return lib.astype_intsafe(arr.ravel(), dtype).reshape(arr.shape)    875     876         # if we have a datetime/timedelta array of objects


pandas\_libs\lib.pyx in pandas._libs.lib.astype_intsafe()


ValueError: invalid literal for int() with base 10: '8U'
df[df.时长=='8U']
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
31638 31644.0 一个被隔绝的世界 46 纪录片/短片 瑞典 2001-10-25 00:00:00 8U 1948 7.8 美国
df.drop(31638,inplace=True)# inplace=False,默认该删除操作不改变原数据,而是返回一个执行删除操作后的新dataframe;# inplace=True,则会直接在原数据上进行删除操作,删除后无法返回。
df['时长']=df['时长'].astype('int')
---------------------------------------------------------------------------ValueError                                Traceback (most recent call last)<ipython-input-24-83bf9b6fa2b3> in <module>----> 1 df['时长']=df['时长'].astype('int')


D:\anaconda\lib\site-packages\pandas\core\generic.py in astype(self, dtype, copy, errors)   5696         else:   5697             # else, only a single dtype is given-> 5698             new_data = self._data.astype(dtype=dtype, copy=copy, errors=errors)   5699             return self._constructor(new_data).__finalize__(self)   5700 


D:\anaconda\lib\site-packages\pandas\core\internals\managers.py in astype(self, dtype, copy, errors)    580     581     def astype(self, dtype, copy: bool = False, errors: str = "raise"):--> 582         return self.apply("astype", dtype=dtype, copy=copy, errors=errors)    583     584     def convert(self, **kwargs):


D:\anaconda\lib\site-packages\pandas\core\internals\managers.py in apply(self, f, filter, **kwargs)    440                 applied = b.apply(f, **kwargs)    441             else:--> 442                 applied = getattr(b, f)(**kwargs)    443             result_blocks = _extend_blocks(applied, result_blocks)    444 


D:\anaconda\lib\site-packages\pandas\core\internals\blocks.py in astype(self, dtype, copy, errors)    623             vals1d = values.ravel()    624             try:--> 625                 values = astype_nansafe(vals1d, dtype, copy=True)    626             except (ValueError, TypeError):    627                 # e.g. astype_nansafe can fail on object-dtype of strings


D:\anaconda\lib\site-packages\pandas\core\dtypes\cast.py in astype_nansafe(arr, dtype, copy, skipna)    872         # work around NumPy brokenness, #1987    873         if np.issubdtype(dtype.type, np.integer):--> 874             return lib.astype_intsafe(arr.ravel(), dtype).reshape(arr.shape)    875     876         # if we have a datetime/timedelta array of objects


pandas\_libs\lib.pyx in pandas._libs.lib.astype_intsafe()


ValueError: invalid literal for int() with base 10: '12J'
df[df.时长=='12J']
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
32943 32949.0 渔业危机 41 纪录片 英国 2009-06-19 00:00:00 12J 2008 8.2 USA
df.drop(32943,inplace=True)
df['时长']=df['时长'].astype('int')
df['时长'][:5]
0    1421    1162    1163    1424    171Name: 时长, dtype: int32

2.2 排序

2.2.1 单值排序

默认排序

df[:10]  ##根据index进行排序
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1.0 控方证人 42995 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2.0 美丽人生 327855 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3.0 阿甘正传 580897 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4.0 霸王别姬 478523 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港
5 5.0 泰坦尼克号 157074 剧情/爱情/灾难 美国 2012-04-10 00:00:00 194 2012 9.4 中国大陆
6 6.0 辛德勒的名单 306904 剧情/历史/战争 美国 1993-11-30 00:00:00 195 1993 9.4 华盛顿首映
7 7.0 新世纪福音战士剧场版:Air/真心为你 新世紀エヴァンゲリオン劇場版 Ai 24355 剧情/动作/科幻/动画/奇幻 日本 1997-07-19 00:00:00 87 1997 9.4 日本
8 8.0 银魂完结篇:直到永远的万事屋 劇場版 銀魂 完結篇 万事屋よ 21513 剧情/动画 日本 2013-07-06 00:00:00 110 2013 9.4 日本
9 9.0 这个杀手不太冷 662552 剧情/动作/犯罪 法国 1994-09-14 00:00:00 133 1994 9.4 法国

按照投票人数进行排序

## 默认升序排列df.sort_values(by='投票人数')[:5]
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
37035 37041.0 魂惊一线 21 惊悚/恐怖 美国 2003-08-21 00:00:00 108 2002 5.3 美国
35589 35595.0 川崎的玫瑰 21 剧情 其他 2009-12-21 00:00:00 100 2009 6.1 美国
1990 1990.0 爱和一颗子弹 21 动作/犯罪 美国 2002-08-30 00:00:00 85 2002 7.0 美国
22869 22875.0 少年邓恩铭 21 剧情/传记 中国大陆 2011-07-01 00:00:00 90 2011 3.8 美国
37267 37273.0 生生舞不息 21 剧情/歌舞 法国 2002-04-12 00:00:00 100 2002 6.8 美国
## 降序排列df.sort_values(by='投票人数',ascending=False)[:5]
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0.0 肖申克的救赎 692795 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
9 9.0 这个杀手不太冷 662552 剧情/动作/犯罪 法国 1994-09-14 00:00:00 133 1994 9.4 法国
22 22.0 盗梦空间 642134 剧情/动作/科幻/悬疑/冒险 美国 2010-09-01 00:00:00 148 2010 9.2 中国大陆
3 3.0 阿甘正传 580897 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
99 99.0 三傻大闹宝莱坞 549808 剧情/喜剧/爱情/歌舞 印度 2011-12-08 00:00:00 171 2009 9.1 中国大陆

按照年代进行排序

df.sort_values(by='年代')[:5]
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
14048 14048.0 利兹大桥 126 短片 英国 1888-10 60 1888 7.2 美国
1700 1700.0 朗德海花园场景 650 短片 英国 1888-10-14 60 1888 8.7 美国
26164 26170.0 恶作剧 51 短片 美国 1905-03-04 00:00:00 60 1890 4.8 美国
10627 10627.0 可怜的比埃洛 176 喜剧/爱情/动画/短片 法国 1892-10-28 60 1892 7.5 法国
14455 14455.0 迪克森实验音膜 121 短片 美国 1905-03-08 00:00:00 60 1894 7.2 美国

2.2.2 多个值排序

先按照评分降序序,再按照投票人数降序

df.sort_values(by=['评分','投票人数'],ascending=False)[:5]
名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
9278 平安结祈 平安結 208 音乐 日本 2012-02-24 00:00:00 60 2012 9.9 美国
13882 武之舞 128 纪录片 中国大陆 1997-02-01 00:00:00 60 34943 9.9 美国
1110 未知电影 76 科幻/纪录片 美国 1905-06-23 00:00:00 75 2001 9.9 美国
23559 未作回答的问题:伯恩斯坦哈佛六讲 61 纪录片 美国 1905-05-29 00:00:00 60 1973 9.9 美国
35470 未知电影 46 纪录片/音乐 韩国 2013-10-31 00:00:00 90 2013 9.9 韩国

先按照评分降序序,再按照投票人数升序

df.sort_values(by=['评分','投票人数'],ascending=[False,True])[:5]
名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
25270 索科洛夫:巴黎现场 43 音乐 法国 2002-11-04 00:00:00 127 2002 9.9 美国
35465 未知电影 46 纪录片/音乐 韩国 2013-10-31 00:00:00 90 2013 9.9 韩国
23556 未作回答的问题:伯恩斯坦哈佛六讲 61 纪录片 美国 1905-05-29 00:00:00 60 1973 9.9 美国
1110 未知电影 76 科幻/纪录片 美国 1905-06-23 00:00:00 75 2001 9.9 美国
9278 平安结祈 平安結 208 音乐 日本 2012-02-24 00:00:00 60 2012 9.9 美国

2.3基本统计分析

2.3.1 描述性统计

dataframe.describe():对dataframe中的数值数据进行描述性统计

df.describe()
Unnamed: 0.1 投票人数 时长 年代 评分
count 38727.000000 38728.000000 38728.000000 38728.000000 38728.000000
mean 19366.615669 6190.442212 89.031424 1998.791753 6.935577
std 11183.251156 26153.495394 83.233344 253.224718 1.270158
min 0.000000 21.000000 1.000000 1888.000000 2.000000
25% 9681.500000 98.000000 60.000000 1990.000000 6.300000
50% 19363.000000 341.000000 92.000000 2005.000000 7.100000
75% 29050.500000 1741.000000 106.000000 2010.000000 7.800000
max 38737.000000 692795.000000 11500.000000 39180.000000 9.900000

通过描述性统计,可以发现一些异常值,很多异常值往往是需要我们逐步去发现的

比如年代的最大值,上映时间的最大值等

df[df.年代>2021]
Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
13882 13882.0 武之舞 128 纪录片 中国大陆 1997-02-01 00:00:00 60 34943 9.9 美国
17115 17115.0 妈妈回来吧-中国打工村的孩子 49 纪录片 日本 2007-04-08 00:00:00 109 39180 8.9 美国
df[df.时长>1000]
名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
19690 怒海余生 54 剧情/家庭/冒险 美国 1937-09-01 00:00:00 11500 1937 7.9 美国
38730 喧闹村的孩子们 36 家庭 瑞典 1986-12-06 00:00:00 9200 1986 8.7 瑞典
df.drop(df[df.年代>2021].index,inplace=True)df.drop(df[df.时长>1000].index,inplace=True)df.describe()
Unnamed: 0.1 投票人数 时长 年代 评分
count 38723.000000 38724.000000 38724.000000 38724.000000 38724.000000
mean 19366.307053 6191.074760 88.501704 1996.982776 6.935379
std 11183.355143 26154.772096 37.708162 19.934715 1.270054
min 0.000000 21.000000 1.000000 1888.000000 2.000000
25% 9680.500000 98.000000 60.000000 1990.000000 6.300000
50% 19363.000000 341.000000 92.000000 2005.000000 7.100000
75% 29050.500000 1741.000000 106.000000 2010.000000 7.800000
max 38737.000000 692795.000000 958.000000 2017.000000 9.900000
##删除 行 后,重新分配 索引index 从0到len(df)的整数序列作为新的indexdf.index=range(len(df))

2.3.2 最值

df['投票人数'].max()
692795
df['投票人数'].min()
5

2.3.3 均值和中值

df['投票人数'].mean()
6190.297004905758
df['投票人数'].median()
341.0

2.3.4 方差和标准差

df['评分'].var()
1.6129445680877672
df['评分'].std()
1.2700175463700363

2.3.5 求和

df['投票人数'].sum()
239750203

2.3.6 相关系数、协方差

## 相关性df[['投票人数','评分']].corr()
投票人数 评分
投票人数 1.00000 0.12293
评分 0.12293 1.00000
## 协方差df[['投票人数','评分']].cov()
投票人数 评分
投票人数 6.840721e+08 4083.474416
评分 4.083474e+03 1.613036

2.3.7 计数

统计电影数量

len(df)
38724
## 某列的所有取值df['产地'].unique()
array(['美国', '意大利', '中国大陆', '日本', '法国', '英国', '韩国', '中国香港', '阿根廷', '德国',       '印度', '其他', '加拿大', '波兰', '泰国', '澳大利亚', '西班牙', '俄罗斯', '中国台湾', '荷兰',       '丹麦', '比利时', 'USA', '苏联', '墨西哥', '巴西', '瑞典', '西德'], dtype=object)
len(df['产地'].unique())
28

产地中包含了一些重复数据,比如美国和USA,德国和西德,俄罗斯和苏联

我们可以通过数据替换的方法将这些相同的国家的电影数据合并一下

df['产地'].replace('USA','美国',inplace=True)df['产地'].replace(['西德','苏联'],['德国','俄罗斯'],inplace=True)len(df['产地'].unique())
25

计算每一年代电影的数量

df['年代'].value_counts()[:10]
2012    20422013    20012008    19632014    18872010    18862011    18662009    18612007    17112015    15912006    1515Name: 年代, dtype: int64

电影产出前5位的国家或地区

df['产地'].value_counts()[:5]
美国      11978日本       5049中国大陆     3802中国香港     2851法国       2815Name: 产地, dtype: int64
df.to_excel('./movie_data2.xlsx')

2.4 数据透视

Pandas提供了一个数据透视表功能,名为pivot_table。

使用pivot_table的一个挑战是,你需要确保你理解你的数据,并清楚的知道你通过透视表解决了什么问题,虽然pivot_table看起来知识一个简单的函数,但是它能够快速的对数据进行强大的分析。

2.4.1 基础形式

pd.set_option('max_columns',100)  ##设置显示的最大列pd.set_option('max_rows',500)  ##设置显示的最大行
pd.pivot_table(df,index=['年代'])#以年代为索引,统计各个年代数值型变量的均值
Unnamed: 0.1 投票人数 时长 评分
年代
1888 7874.000000 388.000000 60.000000 7.950000
1890 26170.000000 51.000000 60.000000 4.800000
1892 10627.000000 176.000000 60.000000 7.500000
1894 16198.000000 112.666667 60.000000 6.633333
1895 13011.500000 959.875000 60.000000 7.575000
1896 17808.250000 984.250000 60.000000 7.037500
1897 23881.000000 67.000000 60.000000 6.633333
1898 6247.500000 578.500000 60.000000 7.450000
1899 9307.500000 71.000000 9.500000 6.900000
1900 11274.571429 175.285714 36.714286 7.228571
1901 12790.500000 164.500000 47.250000 7.250000
1902 18419.166667 1934.166667 34.666667 7.483333
1903 14180.562500 295.625000 29.625000 6.968750
1904 21104.750000 195.875000 41.250000 7.212500
1905 22911.200000 332.600000 43.800000 6.820000
1906 9072.571429 189.857143 30.571429 7.342857
1907 13241.800000 213.600000 31.800000 7.020000
1908 18246.833333 258.833333 34.166667 7.150000
1909 26264.200000 58.600000 20.600000 7.560000
1910 19299.600000 105.200000 41.800000 6.940000
1911 29989.000000 240.000000 25.750000 7.375000
1912 15309.800000 152.200000 16.400000 7.920000
1913 13272.500000 66.125000 57.750000 6.862500
1914 22277.230769 104.923077 25.923077 6.473077
1915 23753.550000 314.900000 56.800000 7.260000
1916 16389.750000 613.666667 43.833333 7.758333
1917 17738.583333 124.416667 31.333333 7.075000
1918 20357.583333 357.083333 35.166667 7.200000
1919 20273.900000 179.850000 62.400000 7.490000
1920 15948.571429 636.500000 59.357143 7.492857
1921 19603.727273 729.818182 57.363636 7.750000
1922 16549.863636 767.090909 66.363636 7.804545
1923 20526.000000 426.000000 74.055556 7.883333
1924 21965.714286 371.785714 81.178571 8.053571
1925 20873.080000 1104.280000 84.440000 7.788000
1926 20306.608696 443.608696 80.304348 7.773913
1927 23167.482759 695.275862 87.241379 7.751724
1928 20164.000000 404.825000 71.775000 7.945000
1929 21806.771429 740.542857 69.371429 7.440000
1930 17119.200000 555.080000 74.160000 7.360000
1931 20332.595238 1468.666667 78.523810 7.483333
1932 21639.162162 600.081081 77.540541 7.294595
1933 19557.580000 729.720000 76.360000 7.430000
1934 21156.686275 776.490196 83.196078 7.519608
1935 22901.913043 887.695652 73.673913 7.515217
1936 17327.916667 1465.466667 76.266667 7.635000
1937 19602.061224 1580.224490 85.510204 7.575510
1938 18559.000000 552.000000 85.973684 7.736842
1939 20467.387755 5911.857143 97.387755 7.520408
1940 18823.846154 5548.743590 92.820513 7.571795
1941 21021.872340 1552.808511 89.127660 7.427660
1942 21499.754717 2607.754717 78.264151 7.554717
1943 19654.561404 742.842105 78.456140 7.615789
1944 18782.722222 1007.370370 81.925926 7.538889
1945 21224.959184 989.020408 86.959184 7.673469
1946 21317.355932 1034.457627 85.016949 7.606780
1947 20075.693333 439.400000 87.120000 7.453333
1948 18607.390805 1186.505747 88.206897 7.657471
1949 19984.168539 641.685393 81.988764 7.646067
1950 20810.868421 2235.026316 80.157895 7.655263
1951 19176.860759 956.101266 85.632911 7.636709
1952 18813.333333 1473.540230 81.528736 7.743678
1953 21198.261364 4786.113636 84.170455 7.567045
1954 19617.843137 2180.245098 85.549020 7.702941
1955 19366.400000 1983.739130 83.669565 7.580000
1956 19593.557823 1054.605442 76.408163 7.600000
1957 19392.785047 2973.579439 87.355140 7.652336
1958 21047.393443 886.196721 82.975410 7.536885
1959 21027.093750 1725.070312 90.070312 7.571875
1960 21695.786260 1446.274809 101.312977 7.569466
1961 22059.382353 3186.833333 98.215686 7.744118
1962 19616.174825 1972.118881 91.615385 7.704895
1963 20402.370629 1184.027972 92.020979 7.536364
1964 18507.351648 1107.763736 89.714286 7.523077
1965 19569.687117 1988.184049 90.478528 7.576074
1966 18060.325843 1325.005618 89.589888 7.517978
1967 19930.590909 1237.289773 91.590909 7.484659
1968 20384.831395 1096.220930 91.744186 7.317442
1969 19794.579710 593.111111 98.666667 7.370048
1970 21448.194737 676.789474 96.973684 7.291053
1971 21019.123288 1368.506849 96.315068 7.155708
1972 20177.792271 2299.096618 96.289855 7.268116
1973 20535.586854 800.103286 94.882629 7.250235
1974 19354.318386 1685.789238 95.318386 7.062332
1975 19728.586735 2222.739796 97.566327 7.071429
1976 20508.030043 1340.618026 95.055794 7.107725
1977 20180.447489 961.461187 98.022831 7.150685
1978 21098.412935 1001.820896 94.467662 7.096517
1979 20317.398230 1886.880531 95.929204 7.293805
1980 19292.218750 2407.683036 94.178571 7.186607
1981 19177.890511 1609.062044 93.321168 7.157299
1982 18469.744361 2142.729323 91.984962 7.297368
1983 18943.649819 1541.191336 92.169675 7.310108
1984 19314.238095 2667.173469 90.918367 7.375170
1985 19842.740625 1593.043750 93.659375 7.280312
1986 19617.614198 2828.506173 89.145062 7.256790
1987 19229.551020 3128.775510 88.938776 7.284548
1988 19828.427110 4800.227621 88.859335 7.265729
1989 19622.770992 2994.417303 88.458015 7.210687
1990 19089.674300 4965.587786 91.882952 7.149109
1991 20162.046341 4685.819512 93.370732 7.154634
1992 18846.887356 5486.133333 92.572414 7.223678
1993 19639.725624 8117.759637 95.269841 7.195692
1994 19227.095142 11479.255061 91.344130 7.262348
1995 19625.791411 8132.605317 94.441718 7.289366
1996 19540.963250 5095.883946 95.243714 7.258801
1997 18817.189944 8243.938547 94.970205 7.330168
1998 18846.972270 7431.790295 91.131716 7.238302
1999 18930.995200 7137.049600 92.457600 7.188000
2000 20264.229822 5907.770178 92.191518 7.134063
2001 19453.687198 8489.757246 90.958937 7.110145
2002 19625.634444 6552.593333 91.584444 7.069778
2003 19434.881178 7891.964248 90.558360 7.137750
2004 18899.299559 8587.632599 90.424670 7.031366
2005 18963.065717 6506.110847 92.080760 7.030008
2006 19053.291749 7278.260726 90.144554 6.914719
2007 19183.157218 6253.837522 86.628288 6.875102
2008 19056.878757 6750.996943 85.144167 6.910647
2009 18659.401397 8717.478775 85.932294 6.748952
2010 18807.106045 9576.387593 83.434252 6.770361
2011 18862.079850 8763.110397 84.125938 6.577010
2012 19460.709109 7082.787463 85.099902 6.458374
2013 18999.526237 7603.723138 84.902049 6.392604
2014 19334.110758 7723.302597 85.997880 6.259777
2015 20216.991201 7846.329353 89.859837 6.142238
2016 19927.410853 7176.019380 91.329457 5.868217
2017 NaN 123456.000000 142.000000 6.935704

2.4.2 多个索引 index=['','']

实际上,大多数的pivot_table参数可以通过列表获取多个值

pd.pivot_table(df,index=['年代','产地'])
Unnamed: 0.1 投票人数 时长 评分
年代 产地
1888 英国 7874.000000 388.000000 60.000000 7.950000
1890 美国 26170.000000 51.000000 60.000000 4.800000
1892 法国 10627.000000 176.000000 60.000000 7.500000
1894 法国 12374.000000 148.000000 60.000000 7.000000
美国 18110.000000 95.000000 60.000000 6.450000
... ... ... ... ... ...
2016 法国 23068.750000 39.000000 93.250000 7.475000
美国 18957.272727 10563.848485 91.984848 6.540909
英国 22602.090909 14607.272727 85.545455 7.200000
韩国 18906.100000 1739.850000 106.100000 5.730000
2017 美国 NaN 123456.000000 142.000000 6.935704

1585 rows × 4 columns

2.4.3 指定需要统计汇总的数据 values

pd.pivot_table(df,index=['年代','产地'],values=['评分'])
评分
年代 产地
1888 英国 7.950000
1890 美国 4.800000
1892 法国 7.500000
1894 法国 7.000000
美国 6.450000
... ... ...
2016 法国 7.475000
美国 6.540909
英国 7.200000
韩国 5.730000
2017 美国 6.935704

1585 rows × 1 columns

2.4.4 指定函数 aggfunc

pd.pivot_table(df,index=['年代','产地'],values=['投票人数'],aggfunc=np.sum)#投票人数的总计数
投票人数
年代 产地
1888 英国 776
1890 美国 51
1892 法国 176
1894 法国 148
美国 190
... ... ...
1965 中国台湾 461
中国大陆 44280
中国香港 1456
俄罗斯 1389
其他 4048

500 rows × 1 columns

通过将“投票人数”和“评分”列进行对应分组,对“产地”实现数据聚合和总结

pd.pivot_table(df,index=['产地'],values=['投票人数','评分'],aggfunc=[np.sum,np.mean])
sum mean
投票人数 评分 投票人数 评分
产地
中国台湾 5237466 4367.200000 8474.864078 7.066667
中国大陆 41435313 23058.000000 10898.293793 6.064703
中国香港 23285389 18457.700000 8167.446159 6.474114
丹麦 394784 1434.700000 1993.858586 7.245960
俄罗斯 486127 3603.500000 1019.134172 7.554507
其他 3053775 13888.200000 1591.336634 7.237207
加拿大 1384765 4868.400000 1915.304288 6.733610
印度 1146271 2453.400000 3210.843137 6.872269
墨西哥 139613 843.400000 1173.218487 7.087395
巴西 357136 733.500000 3536.000000 7.262376
德国 2680983 7428.400000 2597.851744 7.198062
意大利 2502215 5377.300000 3340.740988 7.179306
日本 18000654 36326.000000 3565.191919 7.194692
比利时 170987 1003.300000 1230.122302 7.217986
法国 10213954 20379.000000 3628.402842 7.239432
波兰 159577 1347.000000 881.640884 7.441989
泰国 1564881 1796.100000 5322.724490 6.109184
澳大利亚 1415713 2093.400000 4719.043333 6.978000
瑞典 290077 1423.300000 1510.817708 7.413021
美国 101929660 83208.635704 8509.739522 6.946789
英国 13242919 20780.700000 4796.421224 7.526512
荷兰 144836 1114.500000 934.425806 7.190323
西班牙 1486733 3139.900000 3326.024609 7.024385
阿根廷 258271 843.700000 2226.474138 7.273276
韩国 8761080 8596.400000 6484.885270 6.362990

2.4.5 非数值处理 fillvalue

非数值(NaN)难以处理,如果想移除他们,可以使用 fill_value 将其设置为0

pd.pivot_table(df,index=['产地'],aggfunc=[np.sum,np.mean],fill_value=0)
sum mean
Unnamed: 0.1 年代 投票人数 时长 评分 Unnamed: 0.1 年代 投票人数 时长 评分
产地
中国台湾 11959927 1235388 5237466 53925 4367.200000 19352.632686 1999.009709 8474.864078 87.257282 7.066667
中国大陆 77537941 7621488 41435313 309608 23058.000000 20393.987638 2004.599684 10898.293793 81.432930 6.064703
中国香港 54830747 5676627 23285389 252431 18457.700000 19232.110488 1991.100316 8167.446159 88.541214 6.474114
丹麦 4042735 395820 394784 17444 1434.700000 20417.853535 1999.090909 1993.858586 88.101010 7.245960
俄罗斯 9581404 946797 486127 45753 3603.500000 20086.800839 1984.899371 1019.134172 95.918239 7.554507
其他 38510728 3835622 3053775 167097 13888.200000 20068.122981 1998.760813 1591.336634 87.075039 7.237207
加拿大 14046604 1447780 1384765 57919 4868.400000 19428.221300 2002.461964 1915.304288 80.109267 6.733610
印度 7342014 716133 1146271 43203 2453.400000 20565.865546 2005.974790 3210.843137 121.016807 6.872269
墨西哥 2529161 237145 139613 10929 843.400000 21253.453782 1992.815126 1173.218487 91.840336 7.087395
巴西 2134066 201987 357136 8869 733.500000 21129.366337 1999.871287 3536.000000 87.811881 7.262376
德国 20695017 2059937 2680983 95008 7428.400000 20053.311047 1996.062984 2597.851744 92.062016 7.198062
意大利 15198009 1487142 2502215 77902 5377.300000 20291.066756 1985.503338 3340.740988 104.008011 7.179306
日本 92776242 10097543 18000654 427683 36326.000000 18375.171717 1999.909487 3565.191919 84.706477 7.194692
比利时 2754457 277930 170987 11447 1003.300000 19816.237410 1999.496403 1230.122302 82.352518 7.217986
法国 55059343 5606796 10213954 253073 20379.000000 19559.269272 1991.757016 3628.402842 89.901599 7.239432
波兰 3742447 359652 159577 14613 1347.000000 20676.502762 1987.027624 881.640884 80.734807 7.441989
泰国 5031292 590684 1564881 26002 1796.100000 17113.238095 2009.129252 5322.724490 88.442177 6.109184
澳大利亚 6025504 600896 1415713 25549 2093.400000 20085.013333 2002.986667 4719.043333 85.163333 6.978000
瑞典 3865865 381491 290077 17898 1423.300000 20134.713542 1986.932292 1510.817708 93.218750 7.413021
美国 230843633 23891007 101929660 1070198 83208.635704 19273.911080 1994.573969 8509.739522 89.346969 6.946789
英国 52612699 5512950 13242919 243077 20780.700000 19055.667874 1996.722202 4796.421224 88.039478 7.526512
荷兰 2989646 310199 144836 11685 1114.500000 19288.038710 2001.283871 934.425806 75.387097 7.190323
西班牙 8501520 894710 1486733 40455 3139.900000 19019.060403 2001.588367 3326.024609 90.503356 7.024385
阿根廷 2458212 232468 258271 10638 843.700000 21191.482759 2004.034483 2226.474138 91.706897 7.273276
韩国 24852295 2712969 8761080 134734 8596.400000 18395.481125 2008.119171 6484.885270 99.729090 6.362990

2.4.6 计算总合数据 margins=True

在最后给出一行总和的数据

pd.pivot_table(df,index=['产地'],aggfunc=[np.sum,np.mean],fill_value=0,margins=True)
sum mean
年代 投票人数 时长 评分 年代 投票人数 时长 评分
产地
中国台湾 1235388 5237466 53925 4367.200000 1999.009709 8474.864078 87.257282 7.066667
中国大陆 7621488 41435313 309608 23058.000000 2004.599684 10898.293793 81.432930 6.064703
中国香港 5676627 23285389 252431 18457.700000 1991.100316 8167.446159 88.541214 6.474114
丹麦 395820 394784 17444 1434.700000 1999.090909 1993.858586 88.101010 7.245960
俄罗斯 3006734 3167110 140761 11031.900000 1992.534129 2098.813784 93.280981 7.310736
其他 3837588 3054119 167168 13895.900000 1998.743750 1590.686979 87.066667 7.237448
加拿大 1447780 1384765 57919 4868.400000 2002.461964 1915.304288 80.109267 6.733610
印度 716133 1146271 43203 2453.400000 2005.974790 3210.843137 121.016807 6.872269
墨西哥 237145 139613 10929 843.400000 1992.815126 1173.218487 91.840336 7.087395
巴西 201987 357136 8869 733.500000 1999.871287 3536.000000 87.811881 7.262376
意大利 1487142 2502215 77902 5377.300000 1985.503338 3340.740988 104.008011 7.179306
日本 10101505 18000667 427863 36339.300000 1999.902000 3563.782815 84.708573 7.194476
比利时 277930 170987 11447 1003.300000 1999.496403 1230.122302 82.352518 7.217986
法国 5608811 10213966 253169 20384.700000 1991.765270 3627.118608 89.903764 7.238885
波兰 359652 159577 14613 1347.000000 1987.027624 881.640884 80.734807 7.441989
泰国 590684 1564881 26002 1796.100000 2009.129252 5322.724490 88.442177 6.109184
澳大利亚 600896 1415713 25549 2093.400000 2002.986667 4719.043333 85.163333 6.978000
瑞典 381491 290077 17898 1423.300000 1986.932292 1510.817708 93.218750 7.413021
美国 23892986 101929672 1070310 83216.435704 1994.572669 8509.030136 89.348861 6.946860
英国 5514959 13249562 244005 20789.400000 1996.726647 4797.089790 88.343592 7.526937
荷兰 310199 144836 11685 1114.500000 2001.283871 934.425806 75.387097 7.190323
西班牙 894710 1486733 40455 3139.900000 2001.588367 3326.024609 90.503356 7.024385
阿根廷 232468 258271 10638 843.700000 2004.034483 2226.474138 91.706897 7.273276
韩国 2712969 8761080 134734 8596.400000 2008.119171 6484.885270 99.729090 6.362990
All 77337135 239749731 3428380 268585.635704 1996.982338 6190.764350 88.526868 6.935359

2.4.7 对不同值执行不同函数

可以向aggfunc传递一个字典。不过,这样做有一个副作用,那就是必须将标签做的更加简洁才性。

对各个产地的投票人数求和,对评分求均值

pd.pivot_table(df,index=['产地'],values=['投票人数','评分'],aggfunc={'投票人数':np.sum,'评分':np.mean},fill_value=0)
投票人数 评分
产地
中国台湾 5237466 7.066667
中国大陆 41435313 6.064703
中国香港 23285389 6.474114
丹麦 394784 7.245960
俄罗斯 486127 7.554507
其他 3053775 7.237207
加拿大 1384765 6.733610
印度 1146271 6.872269
墨西哥 139613 7.087395
巴西 357136 7.262376
德国 2680983 7.198062
意大利 2502215 7.179306
日本 18000654 7.194692
比利时 170987 7.217986
法国 10213954 7.239432
波兰 159577 7.441989
泰国 1564881 6.109184
澳大利亚 1415713 6.978000
瑞典 290077 7.413021
美国 101929660 6.946789
英国 13242919 7.526512
荷兰 144836 7.190323
西班牙 1486733 7.024385
阿根廷 258271 7.273276
韩国 8761080 6.362990

对各个年份的投票人数求和,对评分求均值

pd.pivot_table(df,index=['年代'],values=['投票人数','评分'],aggfunc={'投票人数':np.sum,'评分':np.mean},fill_value=0)
投票人数 评分
年代
1888 776 7.950000
1890 51 4.800000
1892 176 7.500000
1894 338 6.633333
1895 7679 7.575000
1896 7874 7.037500
1897 201 6.633333
1898 1157 7.450000
1899 142 6.900000
1900 1227 7.228571
1901 658 7.250000
1902 11605 7.483333
1903 4730 6.968750
1904 1567 7.212500
1905 1663 6.820000
1906 1329 7.342857
1907 1068 7.020000
1908 1553 7.150000
1909 293 7.560000
1910 526 6.940000
1911 960 7.375000
1912 761 7.920000
1913 529 6.862500
1914 2728 6.473077
1915 6298 7.260000
1916 7364 7.758333
1917 1493 7.075000
1918 4285 7.200000
1919 3597 7.490000
1920 8911 7.492857
1921 16056 7.750000
1922 16876 7.804545
1923 7668 7.883333
1924 10410 8.053571
1925 27607 7.788000
1926 10203 7.773913
1927 20163 7.751724
1928 16193 7.945000
1929 25919 7.440000
1930 13877 7.360000
1931 61684 7.483333
1932 22203 7.294595
1933 36486 7.430000
1934 39601 7.519608
1935 40834 7.515217
1936 87928 7.635000
1937 77431 7.575510
1938 20976 7.736842
1939 289681 7.520408
1940 216401 7.571795
1941 72982 7.427660
1942 138211 7.554717
1943 42342 7.615789
1944 54398 7.538889
1945 48462 7.673469
1946 61033 7.606780
1947 32955 7.453333
1948 103226 7.657471
1949 57110 7.646067
1950 169862 7.655263
1951 75532 7.636709
1952 128198 7.743678
1953 421178 7.567045
1954 222385 7.702941
1955 228130 7.580000
1956 155027 7.600000
1957 318173 7.652336
1958 108116 7.536885
1959 220809 7.571875
1960 189462 7.569466
1961 325057 7.744118
1962 282013 7.704895
1963 169316 7.536364
1964 201613 7.523077
1965 324074 7.576074
1966 235851 7.517978
1967 217763 7.484659
1968 188550 7.317442
1969 122774 7.370048
1970 128590 7.291053
1971 299703 7.155708
1972 475913 7.268116
1973 170422 7.250235
1974 375931 7.062332
1975 435657 7.071429
1976 312364 7.107725
1977 210560 7.150685
1978 201366 7.096517
1979 426435 7.293805
1980 539321 7.186607
1981 440883 7.157299
1982 569966 7.297368
1983 426910 7.310108
1984 784149 7.375170
1985 509774 7.280312
1986 916436 7.256790
1987 1073170 7.284548
1988 1876889 7.265729
1989 1176806 7.210687
1990 1951476 7.149109
1991 1921186 7.154634
1992 2386468 7.223678
1993 3579932 7.195692
1994 5670752 7.262348
1995 3976844 7.289366
1996 2634572 7.258801
1997 4426995 7.330168
1998 4288143 7.238302
1999 4460656 7.188000
2000 4318580 7.134063
2001 7029519 7.110145
2002 5897334 7.069778
2003 7505258 7.137750
2004 9746963 7.031366
2005 8217218 7.030008
2006 11026565 6.914719
2007 10700316 6.875102
2008 13252207 6.910647
2009 16223228 6.748952
2010 18061067 6.770361
2011 16351964 6.577010
2012 14463052 6.458374
2013 15215050 6.392604
2014 14573872 6.259777
2015 12483510 6.142238
2016 1851413 5.868217
2017 123456 6.935704

1994年被誉为电影史上伟大的一年,但是通过数据我们可以发现,1994年的平均分并不是很高。1924年的电影平均分最高。

2.4.8 透视表过滤

table = pd.pivot_table(df,index=['年代'],values=['投票人数','评分'],aggfunc={'投票人数':np.sum,'评分':np.mean},fill_value=0)table[table.index==1994]
投票人数 评分
年代
1994 5670752 7.262348
table.sort_values('评分',ascending=False)[:10]
投票人数 评分
年代
1924 10410 8.053571
1888 776 7.950000
1928 16193 7.945000
1912 761 7.920000
1923 7668 7.883333
1922 16876 7.804545
1925 27607 7.788000
1926 10203 7.773913
1916 7364 7.758333
1927 20163 7.751724

2.4.9 按照多个索引来进行汇总

pd.pivot_table(df,index=['产地','年代'],values=['投票人数','评分'],aggfunc={'投票人数':np.sum,'评分':np.mean},fill_value=0)
投票人数 评分
产地 年代
中国台湾 1963 121 6.400000
1965 461 6.800000
1966 51 7.900000
1967 4444 8.000000
1968 178 7.400000
... ... ... ...
韩国 2012 610829 6.064151
2013 1130983 6.098198
2014 453152 5.650833
2015 349808 5.423853
2016 34797 5.730000

1585 rows × 2 columns

3 Pandas进阶

import pandas as pd
import numpy as np
#一个参数 默认起点0,步长为1 输出:[0 1 2]
a = np.arange(3)

#两个参数 默认步长为1 输出[3 4 5 6 7 8]
a = np.arange(3,9)

#三个参数 起点为0,终点为3,步长为0.1 输出[ 0.   0.1  0.2  0.3  0.4  0.5  0.6  0.7  0.8  0.9  1.   1.1  1.2  1.3  1.4 1.5  1.6  1.7  1.8  1.9  2.   2.1  2.2  2.3  2.4  2.5  2.6  2.7  2.8  2.9]
a = np.arange(0, 3, 0.1)

3.1 数据重塑和轴向旋转

(1)层次化索引

层次化索引是pandas的一项重要功能,他能使我们再一个轴上拥有多个索引

Series的层次化索引

两层索引

s=pd.Series(np.arange(1,10),index=[['a','a','a','b','b','c','c','d','d'],[1,2,3,1,2,3,1,2,3]])
s
#有点类似合并单元格?
a  1    1   2    2   3    3b  1    4   2    5c  3    6   1    7d  2    8   3    9dtype: int32
s.index
MultiIndex([('a', 1),            ('a', 2),            ('a', 3),            ('b', 1),            ('b', 2),            ('c', 3),            ('c', 1),            ('d', 2),            ('d', 3)],           )
s['a']# 取外层索引
1    12    23    3dtype: int32
s['a':'c']# 切片 a到c
a  1    1   2    2   3    3b  1    4   2    5c  3    6   1    7dtype: int32
s[:,1]# 取内存索引
a    1b    4c    7dtype: int32

通过unstack方法可以将Series变成一个DataFrame

unstack不堆叠 转换成表格

s.unstack()
1 2 3
a 1.0 2.0 3.0
b 4.0 5.0 NaN
c 7.0 NaN 6.0
d NaN 8.0 9.0
s.unstack().stack()
a  1    1.0   2    2.0   3    3.0b  1    4.0   2    5.0c  1    7.0   3    6.0d  2    8.0   3    9.0dtype: float64

(2)DataFrame的层次化索引

对于DataFrame来说,行和列都能够进行层次化索引。

data=pd.DataFrame(np.arange(12).reshape(4,3))data
0 1 2
0 0 1 2
1 3 4 5
2 6 7 8
3 9 10 11
data=pd.DataFrame(np.arange(12).reshape(4,3),index=[['a','a','b','b'],[1,2,1,2]])data
0 1 2
a 1 0 1 2
2 3 4 5
b 1 6 7 8
2 9 10 11
data=pd.DataFrame(np.arange(12).reshape(4,3),index=[['a','a','b','b'],[1,2,1,2]],columns=[['A','A','B'],['Z','X','C']])data# 有四个索引 决定一个值 二维数据变成了四维数据
A B
Z X C
a 1 0 1 2
2 3 4 5
b 1 6 7 8
2 9 10 11

选取列

data['A']
Z X
a 1 0 1
2 3 4
b 1 6 7
2 9 10

设置索引名称

data.index.names=['row1','row2']data
A B
Z X C
row1 row2
a 1 0 1 2
2 3 4 5
b 1 6 7 8
2 9 10 11

设置列级别名称

data.columns.names=['column1','column2']data
column1 A B
column2 Z X C
row1 row2
a 1 0 1 2
2 3 4 5
b 1 6 7 8
2 9 10 11

行顺序调整 row1,row2交换顺序

data.swaplevel('row1','row2')
column1 A B
column2 Z X C
row2 row1
1 a 0 1 2
2 a 3 4 5
1 b 6 7 8
2 b 9 10 11
层次化——电影数据示列

数据导入

df=pd.read_excel('movie_data2.xlsx')df.head()
Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 产地 上映时间 时长 年代 评分 首映地点
0 0 0.0 肖申克的救赎 692795 剧情/犯罪 美国 1994-09-10 00:00:00 142 1994 9.6 多伦多电影节
1 1 1.0 控方证人 42995 剧情/悬疑/犯罪 美国 1957-12-17 00:00:00 116 1957 9.5 美国
2 2 2.0 美丽人生 327855 剧情/喜剧/爱情 意大利 1997-12-20 00:00:00 116 1997 9.5 意大利
3 3 3.0 阿甘正传 580897 剧情/爱情 美国 1994-06-23 00:00:00 142 1994 9.4 洛杉矶首映
4 4 4.0 霸王别姬 478523 剧情/爱情/同性 中国大陆 1993-01-01 00:00:00 171 1993 9.4 香港
df.index
RangeIndex(start=0, stop=38724, step=1)

set_index:可以把列变成索引

reset_index:把索引变成列

把产地和年代同时设置成索引,产地是外层索引,年代是内层索引

df=df.set_index(['产地','年代'])df.head()
Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
产地 年代
美国 1994 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节
1957 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国
意大利 1997 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利
美国 1994 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映
中国大陆 1993 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港

每一个索引都是一个元组

df.index[0]
('美国', 1994)

获取所有的美国电影,由于产地信息已经变成了索引,因此可以用loc方法

df.loc['美国'].head()
Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
年代
1994 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节
1957 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国
1994 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映
2012 5 5.0 泰坦尼克号 157074 剧情/爱情/灾难 2012-04-10 00:00:00 194 9.4 中国大陆
1993 6 6.0 辛德勒的名单 306904 剧情/历史/战争 1993-11-30 00:00:00 195 9.4 华盛顿首映
此时的索引已经变成了年代

这样做最大的好处就是我们可以简化很多的筛选环节

每一个索引是一个元组

索引交换 swaplevel

df=df.swaplevel('产地','年代')df.head()
Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
年代 产地
1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节
1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国
1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利
1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映
1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港
df.loc[1994]#此时产地成了索引
Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
产地
美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节
美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映
法国 9 9.0 这个杀手不太冷 662552 剧情/动作/犯罪 1994-09-14 00:00:00 133 9.4 法国
美国 314 314.0 34街的 768 剧情/家庭/奇幻 1994-12-23 00:00:00 114 7.9 美国
中国大陆 402 402.0 活着 202794 剧情/家庭 1994-05-18 00:00:00 132 9.0 法国
... ... ... ... ... ... ... ... ... ...
美国 38203 38217.0 鬼精灵2: 恐怖 60 喜剧/恐怖/奇幻 1994-04-08 00:00:00 85 5.8 美国
英国 38333 38347.0 黑色第16 44 剧情/惊悚 1996-02-01 00:00:00 106 6.8 美国
日本 38677 38691.0 蜡笔小新之布里布里王国的秘密宝藏 クレヨンしんちゃん ブリブリ王国の 2142 动画 1994-04-23 00:00:00 94 7.7 日本
日本 38679 38693.0 龙珠Z剧场版10:两人面临危机! 超战士难以成眠 ドラゴンボール Z 劇場版:危険なふたり! 579 动画 1994-03-12 00:00:00 53 7.2 美国
中国香港 38680 38694.0 重案实录之惊天械劫案 重案實錄之驚天械劫 90 动作/犯罪 1905-06-16 00:00:00 114 7.3 美国

494 rows × 9 columns

取消层次化索引 也就是将索引变成了列

df=df.reset_index()
df.head()
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港

(3)数据旋转

行列转化

data=df[:5]#先取前五行data
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港

T 可以直接让数据的行和列进行交换

data.T
0 1 2 3 4
年代 1994 1957 1997 1994 1993
产地 美国 美国 意大利 美国 中国大陆
Unnamed: 0 0 1 2 3 4
Unnamed: 0.1 0 1 2 3 4
名字 肖申克的救赎 控方证人 美丽人生 阿甘正传 霸王别姬
投票人数 692795 42995 327855 580897 478523
类型 剧情/犯罪 剧情/悬疑/犯罪 剧情/喜剧/爱情 剧情/爱情 剧情/爱情/同性
上映时间 1994-09-10 00:00:00 1957-12-17 00:00:00 1997-12-20 00:00:00 1994-06-23 00:00:00 1993-01-01 00:00:00
时长 142 116 116 142 171
评分 9.6 9.5 9.5 9.4 9.4
首映地点 多伦多电影节 美国 意大利 洛杉矶首映 香港

dataframe也可以使用stack和unstack,转化为层次索引的Series

data.stack()
0  年代                             1994   产地                               美国   Unnamed: 0                        0   Unnamed: 0.1                      0   名字                           肖申克的救赎   投票人数                         692795   类型                            剧情/犯罪   上映时间            1994-09-10 00:00:00   时长                              142   评分                              9.6   首映地点                         多伦多电影节1  年代                             1957   产地                               美国   Unnamed: 0                        1   Unnamed: 0.1                      1   名字                             控方证人   投票人数                          42995   类型                         剧情/悬疑/犯罪   上映时间            1957-12-17 00:00:00   时长                              116   评分                              9.5   首映地点                             美国2  年代                             1997   产地                              意大利   Unnamed: 0                        2   Unnamed: 0.1                      2   名字                            美丽人生    投票人数                         327855   类型                         剧情/喜剧/爱情   上映时间            1997-12-20 00:00:00   时长                              116   评分                              9.5   首映地点                            意大利3  年代                             1994   产地                               美国   Unnamed: 0                        3   Unnamed: 0.1                      3   名字                             阿甘正传   投票人数                         580897   类型                            剧情/爱情   上映时间            1994-06-23 00:00:00   时长                              142   评分                              9.4   首映地点                          洛杉矶首映4  年代                             1993   产地                             中国大陆   Unnamed: 0                        4   Unnamed: 0.1                      4   名字                             霸王别姬   投票人数                         478523   类型                         剧情/爱情/同性   上映时间            1993-01-01 00:00:00   时长                              171   评分                              9.4   首映地点                             香港dtype: object
data.stack().unstack()
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点
0 1994 美国 0 0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 142 9.6 多伦多电影节
1 1957 美国 1 1 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 116 9.5 美国
2 1997 意大利 2 2 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 116 9.5 意大利
3 1994 美国 3 3 阿甘正传 580897 剧情/爱情 1994-06-23 142 9.4 洛杉矶首映
4 1993 中国大陆 4 4 霸王别姬 478523 剧情/爱情/同性 1993-01-01 171 9.4 香港

3.2 数据分组、分组运算

GroupBy技术:实现数据的分组,和分组运算,作用类似于数据透视表

按照电影产地进行分组

先定义一个分组变量group

group=df.groupby(df['产地'])
group
<pandas.core.groupby.generic.DataFrameGroupBy object at 0x000001F36ED3CC70>

可以计算分组后的各个统计量

group.mean().head()
年代 Unnamed: 0 Unnamed: 0.1 投票人数 时长 评分
产地
中国台湾 1999.009709 19347.205502 19352.632686 8474.864078 87.257282 7.066667
中国大陆 2004.599684 20388.198843 20393.987638 10898.293793 81.432930 6.064703
中国香港 1991.100316 19226.836198 19232.110488 8167.446159 88.541214 6.474114
丹麦 1999.090909 20412.055556 20417.853535 1993.858586 88.101010 7.245960
俄罗斯 1984.899371 20081.157233 20086.800839 1019.134172 95.918239 7.554507

计算每年的平均评分

df['评分'].groupby(df['年代']).mean().head()
年代1888    7.9500001890    4.8000001892    7.5000001894    6.6333331895    7.575000Name: 评分, dtype: float64

只会对数值变量进行分组运算

#对年代求平均数、求和并没有什么意义,这里将年代转成string类型df['年代']=df['年代'].astype('str')
df.groupby(df['产地']).mean().head()# 这里对年代就没有均值的求取了
Unnamed: 0 Unnamed: 0.1 投票人数 时长 评分
产地
中国台湾 19347.205502 19352.632686 8474.864078 87.257282 7.066667
中国大陆 20388.198843 20393.987638 10898.293793 81.432930 6.064703
中国香港 19226.836198 19232.110488 8167.446159 88.541214 6.474114
丹麦 20412.055556 20417.853535 1993.858586 88.101010 7.245960
俄罗斯 20081.157233 20086.800839 1019.134172 95.918239 7.554507

我们也可以传入多个分组变量

df.groupby([df['产地'],df['年代']]).mean()
Unnamed: 0 Unnamed: 0.1 投票人数 时长 评分
产地 年代
中国台湾 1963 14805.000000 14806.000000 121.000000 113.000000 6.400000
1965 30276.000000 30285.000000 153.666667 105.000000 6.800000
1966 26299.000000 26308.000000 51.000000 60.000000 7.900000
1967 16605.000000 16606.000000 4444.000000 112.000000 8.000000
1968 21276.500000 21285.500000 89.000000 83.000000 7.400000
... ... ... ... ... ... ...
韩国 2012 17576.207547 17580.452830 5762.537736 100.669811 6.064151
2013 18953.117117 18958.252252 10189.036036 96.504505 6.098198
2014 19881.700000 19887.200000 3776.266667 98.666667 5.650833
2015 19036.128440 19040.908257 3209.247706 100.266055 5.423853
2016 18901.350000 18906.100000 1739.850000 106.100000 5.730000

1585 rows × 5 columns

获得每个地区,每一年的电影的评分的均值

df['评分'].groupby([df['产地'],df['年代']]).mean()
产地    年代  中国台湾  1963    6.400000      1965    6.800000      1966    7.900000      1967    8.000000      1968    7.400000                ...   韩国    2012    6.064151      2013    6.098198      2014    5.650833      2015    5.423853      2016    5.730000Name: 评分, Length: 1511, dtype: float64

Series通过unstack方法转化为dataframe——会产生缺失值

df['评分'].groupby([df['产地'],df['年代']]).mean().unstack().head()
年代 1888 1890 1892 1894 1895 1896 1897 1898 1899 1900 ... 2008 2009 2010 2011 2012 2013 2014 2015 2016 2017
产地
中国台湾 NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN ... 7.420000 7.100000 7.053846 7.231818 6.556098 7.076471 6.522222 6.576000 NaN NaN
中国大陆 NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN ... 6.589726 6.536628 6.357831 5.824606 5.727187 5.316667 4.963757 4.969189 4.712000 NaN
中国香港 NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN ... 6.476786 6.442553 6.245455 5.971053 6.110526 6.105714 5.616667 5.589189 5.390909 NaN
丹麦 NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN ... 7.050000 7.118182 7.362500 7.016667 7.418750 6.555556 7.120000 7.166667 7.000000 NaN
俄罗斯 NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN ... 6.741667 6.278571 6.858824 7.040000 6.572727 6.875000 7.175000 7.342857 NaN NaN

5 rows × 127 columns

3.3 离散化处理

再实际的数据分析项目中,对有的数据属性,我们往往并不关注数据的绝对取值,只关注它所处的区间或等级。

比如我们可以把评分9分及以上定义为A,7-9分为B,5-7分为C,3-5分为D,小于3分的为E。

离散化也可以称为分组、区间化

Pandas为我们提供了方便的函数cut():

pd.cut (x, bins, right=True, labels=None, retbins=False, precision=3, include_lowest=False)

参数:

x:需要离散化的数组、Series、DataFrame对象

bins:分组的依据

right=True:默认包括右端点

include_lowest=False:默认不包括左端点

labels:是否要用标记替换分组

retbins:返回x中对应的bins的列表

precision:精度

df['评分等级']=pd.cut(df['评分'],[0,3,5,7,9,10],labels=['E','D','C','B','A'])df
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.600000 多伦多电影节 A
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.500000 美国 A
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.500000 意大利 A
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.400000 洛杉矶首映 A
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.400000 香港 A
... ... ... ... ... ... ... ... ... ... ... ... ...
38719 1935 美国 38719 38734.0 1935年 57 喜剧/歌舞 1935-03-15 00:00:00 98 7.600000 美国 B
38720 1986 中国大陆 38720 38735.0 血溅画屏 95 剧情/悬疑/犯罪/武侠/古装 1905-06-08 00:00:00 91 7.100000 美国 B
38721 1986 中国大陆 38721 38736.0 魔窟中的幻想 51 惊悚/恐怖/儿童 1905-06-08 00:00:00 78 8.000000 美国 B
38722 1977 俄罗斯 38722 38737.0 列宁格勒围困之星火战役 Блокада: Фильм 2: Ленинградский ме... 32 剧情/战争 1905-05-30 00:00:00 97 6.600000 美国 C
38723 2017 美国 38723 NaN 复仇者联盟3 123456 剧情/科幻 2017-05-04 00:00:00 142 6.935704 美国 C

38724 rows × 12 columns

根据投票人数来刻画电影的热门

投票人数越多,热门程度越高

使用 np.percentile 进行分位数计算
a = range(1,101)

求取a数列第90%分位的数值

np.percentile(a, 90)

90.10000000000001

bins=np.percentile(df['投票人数'],[0,20,40,60,80,100])
df['热门程度']=pd.cut(df['投票人数'],bins,labels=['E','D','C','B','A'])
df
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.600000 多伦多电影节 A A
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.500000 美国 A A
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.500000 意大利 A A
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.400000 洛杉矶首映 A A
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.400000 香港 A A
... ... ... ... ... ... ... ... ... ... ... ... ... ...
38719 1935 美国 38719 38734.0 1935年 57 喜剧/歌舞 1935-03-15 00:00:00 98 7.600000 美国 B E
38720 1986 中国大陆 38720 38735.0 血溅画屏 95 剧情/悬疑/犯罪/武侠/古装 1905-06-08 00:00:00 91 7.100000 美国 B D
38721 1986 中国大陆 38721 38736.0 魔窟中的幻想 51 惊悚/恐怖/儿童 1905-06-08 00:00:00 78 8.000000 美国 B E
38722 1977 俄罗斯 38722 38737.0 列宁格勒围困之星火战役 Блокада: Фильм 2: Ленинградский ме... 32 剧情/战争 1905-05-30 00:00:00 97 6.600000 美国 C E
38723 2017 美国 38723 NaN 复仇者联盟3 123456 剧情/科幻 2017-05-04 00:00:00 142 6.935704 美国 C A

38724 rows × 13 columns

大烂片:投票人数多,评分低

df[(df.热门程度=='A')&(df.评分等级=='E')]
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
655 2011 中国大陆 655 655.0 B区 5187 剧情/惊悚/恐怖 2011-06-03 00:00:00 89 2.3 中国大陆 E A
4376 2014 中国大陆 4376 4376.0 怖偶 4867 悬疑/惊悚 2014-05-07 00:00:00 88 2.8 中国大陆 E A
5413 2011 中国大陆 5413 5413.0 床下有人 4309 悬疑/惊悚 2011-10-14 00:00:00 100 2.8 中国大陆 E A
6802 2013 中国大陆 6802 6802.0 帝国秘符 4351 动作/冒险 2013-09-18 00:00:00 93 3.0 中国大陆 E A
8232 2011 中国大陆 8232 8232.0 飞天 4764 剧情 2011-07-01 00:00:00 115 2.9 中国大陆 E A
8406 2014 中国大陆 8406 8406.0 分手达人 3937 喜剧/爱情 2014-06-06 00:00:00 90 2.7 中国大陆 E A
9601 2012 中国大陆 9601 9601.0 孤岛惊魂 2982 悬疑/惊悚/恐怖 2013-01-26 00:00:00 93 2.8 中国大陆 E A
10513 2013 中国大陆 10513 10513.0 海天盛宴·韦口 3788 情色 2013-10-12 00:00:00 88 2.9 网络 E A
16799 2013 中国大陆 16799 16800.0 孪生密码 6390 动作/悬疑 2013-11-08 00:00:00 96 2.9 中国大陆 E A
21530 2010 日本 21530 21539.0 拳皇 6329 动作/科幻/冒险 2012-10-12 00:00:00 93 3.0 中国大陆 E A
22702 2013 中国大陆 22702 22711.0 闪魂 3119 惊悚/犯罪 2014-02-21 00:00:00 94 2.6 中国大陆 E A
22880 2015 中国大陆 22880 22889.0 少年mzd 3058 动画/儿童/冒险 2015-04-30 00:00:00 76 2.4 中国大陆 E A
24125 2013 英国 24125 24134.0 史前怪兽 3543 动作/惊悚/冒险 2014-01-01 00:00:00 89 3.0 中国大陆 E A
28258 2011 中国大陆 28258 28267.0 无极限之危情速递 6319 喜剧/动作/爱情/冒险 2011-08-12 00:00:00 94 2.8 中国大陆 E A
32094 2010 中国大陆 32094 32105.0 异度公寓 3639 惊悚 2010-06-04 00:00:00 93 2.7 中国大陆 E A
32487 2014 中国大陆 32487 32498.0 英雄之战 8359 动作/爱情 2014-03-21 00:00:00 90 3.0 中国大陆 E A
32660 2013 中国大陆 32660 32671.0 咏春小龙 8861 剧情/动作 2013-07-20 00:00:00 90 3.0 中国大陆 E A
33483 2014 中国大陆 33483 33496.0 再爱一次好不好 6999 喜剧/爱情 2014-04-11 00:00:00 94 3.0 中国大陆 E A
38651 2014 中国大陆 38651 38665.0 大话天仙 21629 喜剧/奇幻/古装 2014-02-02 00:00:00 91 3.0 中国大陆 E A
38653 2013 中国大陆 38653 38667.0 天机·富春山居图 74709 动作/冒险 2013-06-09 00:00:00 122 2.9 中国大陆 E A
38654 2014 中国大陆 38654 38668.0 特工艾米拉 10852 动作/悬疑 2014-04-11 00:00:00 96 2.7 中国大陆 E A
38658 2015 中国大陆 38658 38672.0 汽车人总动员 12892 喜剧/动画/冒险 2015-07-03 00:00:00 85 2.3 中国大陆 E A
38663 2016 中国大陆 38663 38677.0 2016年中央电视台春节 17328 歌舞/真人秀 2016-02-07 00:00:00 280 2.3 中国大陆 E A
38669 2014 中国大陆 38669 38683.0 放手爱 29254 喜剧/爱情 2014-04-30 00:00:00 93 2.3 中国大陆 E A

冷门高分电影

df[(df.热门程度=='E')&(df.评分等级=='A')]
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
456 2015 美国 456 456.0 未知电影 45 音乐 2015-12-14 00:00:00 60 9.3 美国 A E
587 2011 英国 587 587.0 BBC喜剧音 38 喜剧/音乐/歌舞 2011-08-13 00:00:00 95 9.3 美国 A E
642 2003 美国 642 642.0 未知电影 38 纪录片/音乐 2003-02-03 00:00:00 55 9.2 美国 A E
686 2014 英国 686 686.0 未知电影 63 音乐/舞台艺术 2014-05-18 00:00:00 49 9.5 美国 A E
698 2008 英国 698 698.0 未知电影 52 纪录片 2008-07-25 00:00:00 40 9.8 美国 A E
... ... ... ... ... ... ... ... ... ... ... ... ... ...
37574 1986 英国 37574 37587.0 歌唱神探 36 剧情/悬疑/歌舞 1986-11-16 00:00:00 415 9.1 美国 A E
37700 1972 美国 37700 37713.0 未知电影 56 纪录片 1972-12-23 00:00:00 70 9.3 美国 A E
38105 1975 美国 38105 38119.0 山那边 70 剧情 1975-11-14 00:00:00 103 9.1 美国 A E
38438 2015 美国 38438 38452.0 62 纪录片/短片 2015-08-19 00:00:00 9 9.1 纽约电影论坛 A E
38494 2007 英国 38494 38508.0 未知电影 41 纪录片/短片 1905-06-29 00:00:00 57 9.2 美国 A E

245 rows × 13 columns

将处理的数据保存

df.to_excel('movies_data3.xlsx')

3.4 合并数据集

(1)append

先把数据集拆分为多个,再进行合并

df_usa=df[df.产地=='美国']df_cn=df[df.产地=='中国大陆']
df_cn.append(df_usa)
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.400000 香港 A A
21 1961 中国大陆 21 21.0 大闹天宫 74881 动画/奇幻 1905-05-14 00:00:00 114 9.200000 上集 A A
29 2015 中国大陆 29 29.0 穹顶之下 51113 纪录片 2015-02-28 00:00:00 104 9.200000 中国大陆 A A
38 1982 中国大陆 38 38.0 茶馆 10678 剧情/历史 1905-06-04 00:00:00 118 9.200000 美国 A A
45 1988 中国大陆 45 45.0 山水情 10781 动画/短片 1905-06-10 00:00:00 19 9.200000 美国 A A
... ... ... ... ... ... ... ... ... ... ... ... ... ...
38712 1987 美国 38712 38726.0 零下的激情 199 剧情/爱情/犯罪 1987-11-06 00:00:00 98 7.400000 美国 B D
38714 1986 美国 38714 38728.0 离别秋波 240 剧情/爱情/音乐 1986-02-19 00:00:00 90 8.200000 美国 B C
38717 1986 美国 38717 38732.0 极乐森林 45 纪录片 1986-09-14 00:00:00 90 8.100000 美国 B E
38719 1935 美国 38719 38734.0 1935年 57 喜剧/歌舞 1935-03-15 00:00:00 98 7.600000 美国 B E
38723 2017 美国 38723 NaN 复仇者联盟3 123456 剧情/科幻 2017-05-04 00:00:00 142 6.935704 美国 C A

15780 rows × 13 columns

(2)merge

pd.merge(left, right, how='inner', on=None, left_on=None, right_on=None,
left_index=False, right_index=False, sort=True,
suffixes=('_x','_y'), copy=True, indicator=False)

left:对象

right:另一个对象

on:要加入的列。必须在左、右综合对象中找到。如果不能通过,left_index和right_index是假,将推断DataFrame中的列的交叉点为连接键

left_on:从左边的综合使用作为键列。可以是列名或数组的长度等于长度综合。

right_on:从右边的综合使用作为键列。可以是列名或数组的长度等于长度综合。

left_index:如果为True,则使用索引(行标签)从左综合作为其连接键。在与多重(层次)的综合,级别数必须匹配连接键从右综合的数目。

right_index:先沟通用法作为正确综合left_index。

how:之一‘左’,‘右’,‘外在’,‘内部’。默认为内联。

sort:综合通过连接键按字典顺序对结果进行排序。默认为True,设置为False在大多数情况下将提高性能。

suffixes:字符串后缀并不适用于重叠列的元组。默认为('_x','_y')

copy:即使重新索引是不必要总是从传递的综合对象,赋值的数据(默认为True)。在许多情况下不能避免,但可能会提高性能/内存使用情况,可以避免赋值上述案件有些病理,但尽管如此提供此选项。

indicator:将列添加到输出综合呼吁_merge与信息源的每一行。_merge是绝对类型,并对观测其合并键只出现在‘左’的综合,关策其合并键只会出现在‘正确’的综合,和两个如果观测合并关键发现在两个 right_only left_only 的值。

选取6部热门电影进行操作

df1=df.loc[:5]df1
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节 A A
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国 A A
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利 A A
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映 A A
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港 A A
5 2012 美国 5 5.0 泰坦尼克号 157074 剧情/爱情/灾难 2012-04-10 00:00:00 194 9.4 中国大陆 A A
df2=df.loc[:5][['名字','产地']]#只想要名字和产地两列df2['票房']=[111,222,333,444,555,666]df2
名字 产地 票房
0 肖申克的救赎 美国 111
1 控方证人 美国 222
2 美丽人生 意大利 333
3 阿甘正传 美国 444
4 霸王别姬 中国大陆 555
5 泰坦尼克号 美国 666
##打乱样本df2=df2.sample(frac=1)df2
名字 产地 票房
5 泰坦尼克号 美国 666
2 美丽人生 意大利 333
4 霸王别姬 中国大陆 555
0 肖申克的救赎 美国 111
1 控方证人 美国 222
3 阿甘正传 美国 444
## 重新设置索引df2.index=range(len(df2))df2
名字 产地 票房
0 泰坦尼克号 美国 666
1 美丽人生 意大利 333
2 霸王别姬 中国大陆 555
3 肖申克的救赎 美国 111
4 控方证人 美国 222
5 阿甘正传 美国 444

对df1和df2进行合并

pd.merge(df1,df2,how='inner',on='名字')
年代 产地_x Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度 产地_y 票房
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节 A A 美国 111
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国 A A 美国 222
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利 A A 意大利 333
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映 A A 美国 444
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港 A A 中国大陆 555
5 2012 美国 5 5.0 泰坦尼克号 157074 剧情/爱情/灾难 2012-04-10 00:00:00 194 9.4 中国大陆 A A 美国 666

两个样本都有 产地 列,所以会有两个产地列

(3)concat

将多个数据集进行批量合并

df1=df[:5]df2=df[100:105]df3=df[200:205]
df1
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节 A A
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国 A A
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利 A A
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映 A A
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港 A A
df2
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
100 1993 韩国 100 100.0 101 146 喜剧/爱情 1993-06-19 00:00:00 112 7.4 韩国 B D
101 1995 英国 101 101.0 10 186 喜剧 1995-01-25 00:00:00 101 7.4 美国 B D
102 2013 韩国 102 102.0 素媛 114819 剧情/家庭 2013-10-02 00:00:00 123 9.1 韩国 A A
103 2003 美国 103 103.0 101忠狗续集:伦敦 924 喜剧/动画/家庭 2003-01-21 00:00:00 70 7.5 美国 B B
104 2000 美国 104 104.0 10 9514 喜剧/家庭 2000-09-22 00:00:00 100 7.0 美国 C A
df3
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
200 2014 日本 200 200.0 最完美的离婚 2014特别篇 18478 剧情/喜剧/爱情 2014-02-08 00:00:00 120 9.1 日本 A A
201 2009 日本 201 201.0 2001夜物 84 剧情/动画 2009-10-02 00:00:00 80 6.6 美国 C D
202 2009 中国香港 202 202.0 头七 頭 7039 恐怖 2009-05-21 00:00:00 60 6.2 美国 C A
203 1896 法国 203 203.0 火车进站 L 7001 纪录片/短片 1896-01-06 60 8.8 法国 B A
204 2009 美国 204 204.0 银行舞蹈 6944 短片 1905-07-01 00:00:00 60 7.8 美国 B A
dff=pd.concat([df1,df2,df3],axis=0) ##默认axis=0 增加行数,axis=1增加列数dff
年代 产地 Unnamed: 0 Unnamed: 0.1 名字 投票人数 类型 上映时间 时长 评分 首映地点 评分等级 热门程度
0 1994 美国 0 0.0 肖申克的救赎 692795 剧情/犯罪 1994-09-10 00:00:00 142 9.6 多伦多电影节 A A
1 1957 美国 1 1.0 控方证人 42995 剧情/悬疑/犯罪 1957-12-17 00:00:00 116 9.5 美国 A A
2 1997 意大利 2 2.0 美丽人生 327855 剧情/喜剧/爱情 1997-12-20 00:00:00 116 9.5 意大利 A A
3 1994 美国 3 3.0 阿甘正传 580897 剧情/爱情 1994-06-23 00:00:00 142 9.4 洛杉矶首映 A A
4 1993 中国大陆 4 4.0 霸王别姬 478523 剧情/爱情/同性 1993-01-01 00:00:00 171 9.4 香港 A A
100 1993 韩国 100 100.0 101 146 喜剧/爱情 1993-06-19 00:00:00 112 7.4 韩国 B D
101 1995 英国 101 101.0 10 186 喜剧 1995-01-25 00:00:00 101 7.4 美国 B D
102 2013 韩国 102 102.0 素媛 114819 剧情/家庭 2013-10-02 00:00:00 123 9.1 韩国 A A
103 2003 美国 103 103.0 101忠狗续集:伦敦 924 喜剧/动画/家庭 2003-01-21 00:00:00 70 7.5 美国 B B
104 2000 美国 104 104.0 10 9514 喜剧/家庭 2000-09-22 00:00:00 100 7.0 美国 C A
200 2014 日本 200 200.0 最完美的离婚 2014特别篇 18478 剧情/喜剧/爱情 2014-02-08 00:00:00 120 9.1 日本 A A
201 2009 日本 201 201.0 2001夜物 84 剧情/动画 2009-10-02 00:00:00 80 6.6 美国 C D
202 2009 中国香港 202 202.0 头七 頭 7039 恐怖 2009-05-21 00:00:00 60 6.2 美国 C A
203 1896 法国 203 203.0 火车进站 L 7001 纪录片/短片 1896-01-06 60 8.8 法国 B A
204 2009 美国 204 204.0 银行舞蹈 6944 短片 1905-07-01 00:00:00 60 7.8 美国 B A

posted @ 2021-06-06 14:53  王陸  阅读(728)  评论(7编辑  收藏  举报