pandas入门

Posted 临风而眠

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了pandas入门相关的知识,希望对你有一定的参考价值。

Pandas入门(3)

准备工作

导入包

import pandas as pd
import numpy as np

读入数据

df=pd.read_excel("movie_data2.xlsx")

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

一.数据重塑和轴向旋转

1.层次化索引

层次化索引能使我们在一个轴上拥有多个索引

①Series的层次化索引

来看一个两层索引

s = pd.Series(np.arange(1, 11), index=[
              ['a', 'a', 'a', 'a', 'a', 'b', 'b', 'b', 'c', 'c'],['①', '②', '③', '④', '⑤', '①', '②', '③', '①', '②']])
s

运行结果:

a  ①     1
   ②     2
   ③     3
   ④     4
   ⑤     5
b  ①     6
   ②     7
   ③     8
c  ①     9
   ②    10
dtype: int32
s.index

运行结果:

MultiIndex([('a', '①'),
            ('a', '②'),
            ('a', '③'),
            ('a', '④'),
            ('a', '⑤'),
            ('b', '①'),
            ('b', '②'),
            ('b', '③'),
            ('c', '①'),
            ('c', '②')],
           )

对外层索引进行操作

s['a']

运行结果:

①    1
②    2
③    3
④    4
⑤    5
dtype: int32
#切片
s['a':'b']
#和原生切片不一样,两边都是闭

运行结果:

a  ①    1
   ②    2
   ③    3
   ④    4
   ⑤    5
b  ①    6
   ②    7
   ③    8
dtype: int32

对内层操作

#逗号前面表示外层索引,冒号两边没东西那就是全取
s[:,'①']
#取出来了('a', '①'),('b', '①'),('c', '①')的值

运行结果:

a    1
b    6
c    9
dtype: int32

取具体的值

s['c','②']

运行结果:

10

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

例如:

s.unstack()

运行结果:

a1.02.03.04.05.0
b6.07.08.0NaNNaN
c9.010.0NaNNaNNaN
s.unstack().stack()

运行结果:

a  ①     1.0
   ②     2.0
   ③     3.0
   ④     4.0
   ⑤     5.0
b  ①     6.0
   ②     7.0
   ③     8.0
c  ①     9.0
   ②    10.0
dtype: float64
#stack堆叠:将列转到行, unstack为反操作:行转到列
s.unstack().stack().unstack()

运行结果:

a1.02.03.04.05.0
b6.07.08.0NaNNaN
c9.010.0NaNNaNNaN

③DataFrame的层次化索引

DataFrame的行和列都可以层次化索引

data=pd.DataFrame(np.arange(12).reshape(4,3))
data
#默认索引是数字
012
0012
1345
2678
391011

行的层次化,增加index参数

data2 = pd.DataFrame(np.arange(12).reshape(4, 3),index=[['一','二','二','二'],['a','a','b','c']])
data2
#默认索引是数字
012
a012
a345
b678
c91011

列的层次化,增加columns参数

data3 = pd.DataFrame(np.arange(12).reshape(4, 3), index=[
                     ['一', '二', '二', '二'], ['a', 'a', 'b', 'c']],columns=[['(1)','(1)','(2)'],['Ⅰ','Ⅰ','Ⅱ']])
data3
#默认索引是数字
(1)(2)
a012
a345
b678
c91011

注意像上面那样写(1)的话,要加单引号,否则会被认为是只有一个数字的元组(只有一个数字没有逗号的元组就是数字本身)

选取列

data3['(1)']
a01
a34
b67
c910

给行索引设定名称

data3.index.names=['row1','row2']
data3
(1)(2)
row1row2
a012
a345
b678
c91011

给列索引设定名称

data3.columns.names=['col1','col2']
data3
col1(1)(2)
col2
row1row2
a012
a345
b678
c91011

调整行索引的顺序

data3.swaplevel('row1','row2')
col1(1)(2)
col2
row2row1
a012
345
b678
c91011

④将豆瓣电影数据处理成多索引结构

df.index

运行结果:

RangeIndex(start=0, stop=38722, step=1)

set_index可以把列变成索引, reset_index可以把索引变成列

将产地作为外索引,年代作为内索引

df2=df.set_index(['产地','年代'])
df2
名字投票人数类型上映时间时长评分首映地点
产地年代
美国1994肖申克的救赎692795剧情/犯罪1994-09-10 00:00:001429.6多伦多电影节
1957控方证人42995剧情/悬疑/犯罪1957-12-17 00:00:001169.5美国
意大利1997美丽人生327855剧情/喜剧/爱情1997-12-20 00:00:001169.5意大利
美国1994阿甘正传580897剧情/爱情1994-06-23 00:00:001429.4洛杉矶首映
中国大陆1993霸王别姬478523剧情/爱情/同性1993-01-01 00:00:001719.4香港
...........................
法国1983神学院 S46Adult1905-06-05 00:00:00588.6美国
美国19351935年57喜剧/歌舞1935-03-15 00:00:00987.6美国
中国大陆1986血溅画屏95剧情/悬疑/犯罪/武侠/古装1905-06-08 00:00:00917.1美国
1986魔窟中的幻想51惊悚/恐怖/儿童1905-06-08 00:00:00788.0美国
俄罗斯1977列宁格勒围困之星火战役 Блокада: Фильм 2: Ленинградский ме...32剧情/战争1905-05-30 00:00:00976.6美国

38722 rows × 7 columns

这样的情况下,每一个索引都是一个元组

df2.index[0]

运行结果:

('美国', 1994)
df2.index[1]

运行结果:

('美国', 1957)

若要获取所有的美国电影信息,此时产地已经变成了索引,要用.loc()

.loc根据行标签获取行数据,下面会获得以年代为索引的dataframe

df2.loc['美国']
名字投票人数类型上映时间时长评分首映地点
年代
1994肖申克的救赎692795剧情/犯罪1994-09-10 00:00:001429.6多伦多电影节
1957控方证人42995剧情/悬疑/犯罪1957-12-17 00:00:001169.5美国
1994阿甘正传580897剧情/爱情1994-06-23 00:00:001429.4洛杉矶首映
2012泰坦尼克号157074剧情/爱情/灾难2012-04-10 00:00:001949.4中国大陆
1993辛德勒的名单306904剧情/历史/战争1993-11-30 00:00:001959.4华盛顿首映
........................
1987跷家的一夜82喜剧/动作/惊悚/冒险1987-07-01 00:00:001027.8美国
1987零下的激情199剧情/爱情/犯罪1987-11-06 00:00:00987.4美国
1986离别秋波240剧情/爱情/音乐1986-02-19 00:00:00908.2美国
1986极乐森林45纪录片1986-09-14 00:00:00908.1美国
19351935年57喜剧/歌舞1935-03-15 00:00:00987.6美国

11976 rows × 7 columns

df2.loc['中国大陆']
名字投票人数类型上映时间时长评分首映地点
年代
1993霸王别姬478523剧情/爱情/同性1993-01-01 00:00:001719.4香港
1961大闹天宫74881动画/奇幻1905-05-14 00:00:001149.2上集
2015穹顶之下51113纪录片2015-02-28 00:00:001049.2中国大陆
1982茶馆10678剧情/历史1905-06-04 00:00:001189.2美国
1988山水情10781动画/短片1905-06-10 00:00:00199.2美国
........................
1986T省的八四、八五380剧情1905-06-08 00:00:00948.7美国
1986失踪的女中学生101儿童1905-06-08 00:00:001027.4美国
1986血战台儿庄2908战争1905-06-08 00:00:001208.1美国
1986血溅画屏95剧情/悬疑/犯罪/武侠/古装1905-06-08 00:00:00917.1美国
1986魔窟中的幻想51惊悚/恐怖/儿童1905-06-08 00:00:00788.0美国

3802 rows × 7 columns

调整行索引的顺序

df2=df2.swaplevel('产地','年代')
df2.head()
名字投票人数类型上映时间时长评分首映地点
年代产地
1994美国肖申克的救赎692795剧情/犯罪1994-09-10 00:00:001429.6多伦多电影节
1957美国控方证人42995剧情/悬疑/犯罪1957-12-17 00:00:001169.5美国
1997意大利美丽人生327855剧情/喜剧/爱情1997-12-20 00:00:001169.5意大利
1994美国阿甘正传580897剧情/爱情1994-06-23 00:00:001429.4洛杉矶首映
1993中国大陆霸王别姬478523剧情/爱情/同性1993-01-01 00:00:001719.4香港
df2.loc[1994]

运行结果:

名字投票人数类型上映时间时长评分首映地点
产地
美国肖申克的救赎692795剧情/犯罪1994-09-10 00:00:001429.6多伦多电影节
美国阿甘正传580897剧情/爱情1994-06-23 00:00:001429.4洛杉矶首映
法国这个杀手不太冷662552剧情/动作/犯罪1994-09-14 00:00:001339.4法国
美国34街的768剧情/家庭/奇幻1994-12-23 00:00:001147.9美国
中国大陆活着202794剧情/家庭1994-05-18 00:00:001329.0法国
........................
美国鬼精灵2: 恐怖60喜剧/恐怖/奇幻1994-04-08 00:00:00855.8美国
英国黑色第1644剧情/惊悚1996-02-01 00:00:001066.8美国
日本蜡笔小新之布里布里王国的秘密宝藏 クレヨンしんちゃん ブリブリ王国の2142动画1994-04-23 00:00:00947.7日本
日本龙珠Z剧场版10:两人面临危机! 超战士难以成眠 ドラゴンボール Z 劇場版:危険なふたり!579动画1994-03-12 00:00:00537.2美国
中国香港重案实录之惊天械劫案 重案實錄之驚天械劫90动作/犯罪1905-06-16 00:00:001147.3美国

494 rows × 7 columns

若要取消层次化索引

df2 = df2.reset_index()
df2.head()

运行结果:

年代产地名字投票人数类型上映时间时长评分首映地点
01994美国肖申克的救赎692795剧情/犯罪1994-09-10 00:00:001429.6多伦多电影节
11957美国控方证人42995剧情/悬疑/犯罪1957-12-17 00:00:001169.5美国
21997意大利美丽人生327855剧情/喜剧/爱情1997-12-20 00:00:001169.5意大利
31994美国阿甘正传580897剧情/爱情1994-06-23 00:00:001429.4洛杉矶首映
41993中国大陆霸王别姬478523剧情/爱情/同性1993-01-01 00:00:001719.4香港

2.轴向旋转

取前五行电影数据为例子

Data=df2[:5]
Data
年代产地名字投票人数类型上映时间时长评分首映地点
01994美国肖申克的救赎692795剧情/犯罪1994-09-10 00:00:001429.6多伦多电影节
11957美国控方证人42995剧情/悬疑/犯罪1957-12-17 00:00:001169.5美国
21997意大利美丽人生327855剧情/喜剧/爱情1997-12-20 00:00:001169.5意大利
31994美国阿甘正传580897剧情/爱情1994-06-23 00:00:001429.4洛杉矶首映
41993中国大陆霸王别姬478523剧情/爱情/同性1993-01-01 00:00:001719.4香港

行列转换.T方法

Data.T
01234
年代19941957199719941993
产地美国美国意大利美国中国大陆
名字肖申克的救赎控方证人美丽人生阿甘正传霸王别姬
投票人数69279542995327855580897478523
类型剧情/犯罪剧情/悬疑/犯罪剧情/喜剧/爱情剧情/爱情剧情/爱情/同性
上映时间1994-09-10 00:00:001957-12-17 00:00:001997-12-20 00:00:001994-06-23 00:00:001993-01-01 00:00:00
时长142116116142171
评分9.69.59.59.49.4
首映地点多伦多电影节美国意大利洛杉矶首映香港

DataFrame也可以用stack和unstack转换为层次化索引的Series

Data.stack()

运行结果:

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

二.数据分组,分组运算

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

按照电影产地进行分组

先定义一个分组变量
group=df.groupby(df['产地'])
#GroupBy对象
print(group)
print(type(group))

运行结果:

<pandas.core.groupby.generic.DataFrameGroupBy object at 0x00000214044DE2E0>
<class 'pandas.core.groupby.generic.DataFrameGroupBy'>
计算分组后的各个统计量
#计算各个组别的数值型数据的平均值
group.mean()
投票人数时长年代评分
产地
中国台湾8474.86407887.2572821999.0097097.066667
中国大陆10898.29379381.4329302004.5996846.064703
中国香港8167.44615988.5412141991.1003166.474114
丹麦1993.85858688.1010101999.0909097.245960
俄罗斯1019.13417295.9182391984.8993717.554507
其他1591.49400787.1005731998.7613347.237467
加拿大1915.30428880.1092672002.4619646.733610
印度3210.843137121.0168072005.9747906.872269
墨西哥1173.21848791.8403361992.8151267.087395
巴西3536.00000087.8118811999.8712877.262376
德国2597.85174492.0620161996.0629847.198062
意大利3340.740988104.0080111985.5033387.179306
日本3565.87658584.7054281999.9070927.194572
比利时1230.12230282.3525181999.4964037.217986
法国3628.40284289.9015991991.7570167.239432
波兰881.64088480.7348071987.0276247.441989
泰国5322.72449088.4421772009.1292526.109184
澳大利亚4719.04333385.1633332002.9866676.978000
瑞典1510.81770893.2187501986.9322927.413021
美国8500.82523489.3471111994.5733136.946685
英国4797.08979088.3435921996.7266477.526937
荷兰934.42580675.3870972001.2838717.190323
西班牙3326.02460990.5033562001.5883677.024385
阿根廷2226.47413891.7068972004.0344837.273276
韩国6484.88527099.7290902008.1191716.362990
计算每年的平均评分
df['评分'].groupby(df['年代']).mean()

运行结果:

年代
1888    7.950000
1890    4.800000
1892    7.500000
1894    6.633333
1895    7.575000
          ...   
2012    6.457717
2013    6.392604
2014    6.259777
2015    6.142238
2016    5.868217
Name: 评分, Length: 126, dtype: float64
计算每个产地的电影的平均得分
df['评分'].groupby(df['产地']).mean()

运行结果:

产地
中国台湾    7.066667
中国大陆    6.064703
中国香港    6.474114
丹麦      7.245960
俄罗斯     7.554507
其他      7.237467
加拿大     6.733610
印度      6.872269
墨西哥     7.087395
巴西      7.262376
德国      7.198062
意大利     7.179306
日本      7.194572
比利时     7.217986
法国      7.239432
波兰      7.441989
泰国      6.109184
澳大利亚    6.978000
瑞典      7.413021
美国      6.946685
英国      7.526937
荷兰      7.190323
西班牙     7.024385
阿根廷     7.273276
韩国      6.362990
Name: 评分, dtype: float64
前面的对各个数值型变量求均值,但其实对年代求平均值没啥意义,可以先将年代转为字符串
df['年代']=df['年代'].astype('str')
df.groupby(df['产地']).mean()
投票人数时长评分
产地
中国台湾8474.86407887.2572827.066667
中国大陆10898.29379381.4329306.064703
中国香港8167.44615988.5412146.474114
丹麦1993.85858688.1010107.245960
俄罗斯1019.13417295.9182397.554507
其他1591.49400787.1005737.237467
加拿大1915.30428880.1092676.733610
印度3210.843137121.0168076.872269
墨西哥1173.21848791.8403367.087395
巴西3536.00000087.8118817.262376
德国2597.85174492.0620167.198062
意大利3340.740988104.0080117.179306
日本3565.87658584.7054287.194572
比利时1230.12230282.3525187.217986
法国3628.40284289.9015997.239432
波兰881.64088480.7348077.441989
泰国5322.72449088.4421776.109184
澳大利亚4719.04333385.1633336.978000
瑞典1510.81770893.2187507.413021
美国8500.82523489.3471116.946685
英国4797.08979088.3435927.526937
荷兰934.42580675.3870977.190323
西班牙3326.02460990.5033567.024385
阿根廷2226.47413891.7068977.273276
韩国6484.88527099.7290906.362990

这时候就不会对年代求平均了

#求中位数
df.groupby(df.产地).median()
投票人数时长评分
产地
中国台湾487.092.07.1
中国大陆501.590.06.4
中国香港637.092.06.5
丹麦181.593.57.3
俄罗斯132.093.07.7
其他154.090.07.4
加拿大251.089.06.9
印度138.0131.07.0
墨西哥174.093.07.2
巴西126.096.07.3
德国208.594.07.3
意大利181.0101.07.3
日本355.589.07.3
比利时226.090.07.3
法国240.095.07.3
波兰174.087.07.5
泰国542.592.56.2
澳大利亚303.594.07.0
瑞典186.095.57.6
美国392.093.07.1
英国316.591.07.6
荷兰175.084.07.3
西班牙254.097.07.1
阿根廷140.095.57.3
韩国998.0104.06.5
传入多个分组变量
df.groupby([df['产地'],df["年代"]]).mean()
投票人数时长评分
产地年代
中国台湾1963121.000000113.0000006.400000
1965153.666667105.0000006.800000
196651.00000060.0000007.900000
19674444.000000112.0000008.000000
196889.00000083.0000007.400000
...............
韩国20125762.537736100.6698116.064151
201310189.03603696.5045056.098198
20143776.26666798.6666675.650833
20153209.247706100.2660555.423853
20161739.850000106.1000005.730000

1584 rows × 3 columns

获得每个地区,每一年电影的评分的均值
means=df['评分'].groupby([df['产地'],df['年代']]).mean()
means

运行结果:

产地    年代  
中国台湾  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.730000
Name: 评分, Length: 1584, dtype: float64
series通过unstack方法转化为dataframe,会产生缺失值
means.unstack().T

运行结果:

产地中国台湾中国大陆中国香港丹麦俄罗斯其他加拿大印度墨西哥巴西...波兰泰国澳大利亚瑞典美国英国荷兰西班牙阿根廷韩国
年代
1888NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN...NaNNaNNaNNaNNaN7.950000NaNNaNNaNNaN
1890NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN...NaNNaNNaNNaN4.800000NaNNaNNaNNaNNaN
1892NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN...NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN
1894NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN...NaNNaNNaNNaN6.450000NaNNaNNaNNaNNaN
1895NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN...NaNNaNNaNNaNNaNNaNNaNNaNNaNNaN
..................................................................
20126.5560985.7271876.1105267.4187506.5727276.5917436.4250006.5026327.1000007.32...7.0666675.9629636.6142865.96256.4376227.2931036.7666676.5952386.4833336.064151
20137.0764715.3166676.1057146.5555566.8750006.8535716.0181826.4000006.9833338.00...6.9666675.5680006.7600007.10006.3396687.4483226.5636366.3583336.6166676.098198
20146.5222224.9637575.6166677.1200007.1750006.5962505.9217396.3741947.2500006.86...7.0600005.6535716.5687506.96006.4159227.2750007.3000006.8687507.1500005.650833
20156.5760004.9691895.5891897.1666677.3428576.7357146.0187506.7363646.5000006.76...6.3000005.8466676.8800007.62506.2786417.1550566.7000006.5142867.2333335.423853
2016NaN4.7120005.3909097.000000NaN7.2250006.2000006.900000NaNNaN...NaNNaNNaNNaN6.5409097.200000NaNNaNNaN5.730000

126 rows × 25 columns

三.离散化处理

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

1.cut函数进行离散化

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

pd.cut(x, bins, right=True, labels=None, retbins=False, plecision=3, include_lowest=False)
参数解释︰×∶需要离散化的数组、Series、DataFrame对象

bins :分组的依据

right=True 默认包括右端点(默认左开右闭区间)

比如,我们可以把评分9分及以上的电影定义为A,7到9分定义为B,5到7分定义为c,3到5分定义为D,小于3分定义为E

#x:需要离散化的数组:评分 bins:分组的依据[0,3,5,7,9] 默认左开右闭区间
pd.cut(df以上是关于pandas入门的主要内容,如果未能解决你的问题,请参考以下文章

pandas GroupBy上的方法apply:一般性的“拆分-应用-合并”

pandas入门指南

text [检查特定的数据片段]取自论文但有意思应用。 #python #pandas

python之pandas入门操作

pandas入门

Atom编辑器入门到精通 Atom使用进阶