4 Pandas 数据分析入门¶
学习目标¶
- 掌握在Pandas中计算常用统计量的方法
- 熟练使用pandas进行简单排序、分组、聚合等计算
1 计算常用统计值¶
- 加载数据之后,可以通过计算最大值,最小值,平均值,分位数,方差等方式对数据的分布情况做基本了解
college = pd.read_csv('data/college.csv')
college.head()
输出结果
INSTNM CITY STABBR HBCU MENONLY WOMENONLY RELAFFIL SATVRMID SATMTMID DISTANCEONLY ... UGDS_2MOR UGDS_NRA UGDS_UNKN PPTUG_EF CURROPER PCTPELL PCTFLOAN UG25ABV MD_EARN_WNE_P10 GRAD_DEBT_MDN_SUPP 0 Alabama A & M University Normal AL 1.0 0.0 0.0 0 424.0 420.0 0.0 ... 0.0000 0.0059 0.0138 0.0656 1 0.7356 0.8284 0.1049 30300 33888 1 University of Alabama at Birmingham Birmingham AL 0.0 0.0 0.0 0 570.0 565.0 0.0 ... 0.0368 0.0179 0.0100 0.2607 1 0.3460 0.5214 0.2422 39700 21941.5 2 Amridge University Montgomery AL 0.0 0.0 0.0 1 NaN NaN 1.0 ... 0.0000 0.0000 0.2715 0.4536 1 0.6801 0.7795 0.8540 40100 23370 3 University of Alabama in Huntsville Huntsville AL 0.0 0.0 0.0 0 595.0 590.0 0.0 ... 0.0172 0.0332 0.0350 0.2146 1 0.3072 0.4596 0.2640 45500 24097 4 Alabama State University Montgomery AL 1.0 0.0 0.0 0 425.0 430.0 0.0 ... 0.0098 0.0243 0.0137 0.0892 1 0.7347 0.7554 0.1270 26600 33118.5 5 rows × 27 columns
- 数据字段
college.columns
输出结果
Index(['INSTNM', 'CITY', 'STABBR', 'HBCU', 'MENONLY', 'WOMENONLY', 'RELAFFIL', 'SATVRMID', 'SATMTMID', 'DISTANCEONLY', 'UGDS', 'UGDS_WHITE', 'UGDS_BLACK', 'UGDS_HISP', 'UGDS_ASIAN', 'UGDS_AIAN', 'UGDS_NHPI', 'UGDS_2MOR', 'UGDS_NRA', 'UGDS_UNKN', 'PPTUG_EF', 'CURROPER', 'PCTPELL', 'PCTFLOAN', 'UG25ABV', 'MD_EARN_WNE_P10', 'GRAD_DEBT_MDN_SUPP'], dtype='object')
- 查看数据行列数
college.shape
输出结果
(7535, 27)
- 统计数值列,并进行转置
college.describe().T
输出结果
count mean std min 25% 50% 75% max HBCU 7164.0 0.014238 0.118478 0.0 0.000000 0.00000 0.000000 1.0000 MENONLY 7164.0 0.009213 0.095546 0.0 0.000000 0.00000 0.000000 1.0000 WOMENONLY 7164.0 0.005304 0.072642 0.0 0.000000 0.00000 0.000000 1.0000 RELAFFIL 7535.0 0.190975 0.393096 0.0 0.000000 0.00000 0.000000 1.0000 SATVRMID 1185.0 522.819409 68.578862 290.0 475.000000 510.00000 555.000000 765.0000 SATMTMID 1196.0 530.765050 73.469767 310.0 482.000000 520.00000 565.000000 785.0000 DISTANCEONLY 7164.0 0.005583 0.074519 0.0 0.000000 0.00000 0.000000 1.0000 UGDS 6874.0 2356.837940 5474.275871 0.0 117.000000 412.50000 1929.500000 151558.0000 UGDS_WHITE 6874.0 0.510207 0.286958 0.0 0.267500 0.55570 0.747875 1.0000 UGDS_BLACK 6874.0 0.189997 0.224587 0.0 0.036125 0.10005 0.257700 1.0000 UGDS_HISP 6874.0 0.161635 0.221854 0.0 0.027600 0.07140 0.198875 1.0000 UGDS_ASIAN 6874.0 0.033544 0.073777 0.0 0.002500 0.01290 0.032700 0.9727 UGDS_AIAN 6874.0 0.013813 0.070196 0.0 0.000000 0.00260 0.007300 1.0000 UGDS_NHPI 6874.0 0.004569 0.033125 0.0 0.000000 0.00000 0.002500 0.9983 UGDS_2MOR 6874.0 0.023950 0.031288 0.0 0.000000 0.01750 0.033900 0.5333 UGDS_NRA 6874.0 0.016086 0.050172 0.0 0.000000 0.00000 0.011700 0.9286 UGDS_UNKN 6874.0 0.045181 0.093440 0.0 0.000000 0.01430 0.045400 0.9027 PPTUG_EF 6853.0 0.226639 0.246470 0.0 0.000000 0.15040 0.376900 1.0000 CURROPER 7535.0 0.923291 0.266146 0.0 1.000000 1.00000 1.000000 1.0000 PCTPELL 6849.0 0.530643 0.225544 0.0 0.357800 0.52150 0.712900 1.0000 PCTFLOAN 6849.0 0.522211 0.283616 0.0 0.332900 0.58330 0.745000 1.0000 UG25ABV 6718.0 0.410021 0.228939 0.0 0.241500 0.40075 0.572275 1.0000
- 统计对象和类型列
- pandas 基于 numpy,numpy支持的数据类型,pandas都支持
- np.object 字符串类型
import numpy as np
college.describe(include='all') # 统计所有的列 包括数值列和类别类型 字符串类型
college.describe(include=object) # 类别类型 字符串类型
输出结果
count unique top freq INSTNM 7535 7535 Institute of American Indian and Alaska Native... 1 CITY 7535 2514 New York 87 STABBR 7535 59 CA 773 MD_EARN_WNE_P10 6413 598 PrivacySuppressed 822 GRAD_DEBT_MDN_SUPP 7503 2038 PrivacySuppressed 1510
- 通过info 方法了解不同字段的条目数量,数据类型,是否缺失及内存占用情况
college.info()
输出结果
<class 'pandas.core.frame.DataFrame'> RangeIndex: 7535 entries, 0 to 7534 Data columns (total 27 columns): INSTNM 7535 non-null object CITY 7535 non-null object STABBR 7535 non-null object HBCU 7164 non-null float64 MENONLY 7164 non-null float64 WOMENONLY 7164 non-null float64 RELAFFIL 7535 non-null int64 SATVRMID 1185 non-null float64 SATMTMID 1196 non-null float64 DISTANCEONLY 7164 non-null float64 UGDS 6874 non-null float64 UGDS_WHITE 6874 non-null float64 UGDS_BLACK 6874 non-null float64 UGDS_HISP 6874 non-null float64 UGDS_ASIAN 6874 non-null float64 UGDS_AIAN 6874 non-null float64 UGDS_NHPI 6874 non-null float64 UGDS_2MOR 6874 non-null float64 UGDS_NRA 6874 non-null float64 UGDS_UNKN 6874 non-null float64 PPTUG_EF 6853 non-null float64 CURROPER 7535 non-null int64 PCTPELL 6849 non-null float64 PCTFLOAN 6849 non-null float64 UG25ABV 6718 non-null float64 MD_EARN_WNE_P10 6413 non-null object GRAD_DEBT_MDN_SUPP 7503 non-null object dtypes: float64(20), int64(2), object(5) memory usage: 1.6+ MB
2 常用排序方法¶
2.1 从最大的N个值中选取最小值——找到小成本高口碑电影¶
movie = pd.read_csv('data/movie.csv')
movie2 = movie[['movie_title', 'imdb_score', 'budget']]
movie2.head()
输出结果
movie_title imdb_score budget 0 Avatar 7.9 237000000.0 1 Pirates of the Caribbean: At World's End 7.1 300000000.0 2 Spectre 6.8 245000000.0 3 The Dark Knight Rises 8.5 250000000.0 4 Star Wars: Episode VII - The Force Awakens 7.1 NaN
- 用nlargest方法,选出imdb_score分数最高的100个
movie2.nlargest(100, 'imdb_score').head()
输出结果
movie_title imdb_score budget 2725 Towering Inferno 9.5 NaN 1920 The Shawshank Redemption 9.3 25000000.0 3402 The Godfather 9.2 6000000.0 2779 Dekalog 9.1 NaN 4312 Kickboxer: Vengeance 9.1 17000000.0
- 使用nsmallest方法再从中挑出预算最小的五部
movie2.nlargest(100, 'imdb_score').nsmallest(5, 'budget')
输出结果
movie_title imdb_score budget 4804 Butterfly Girl 8.7 180000.0 4801 Children of Heaven 8.5 180000.0 4706 12 Angry Men 8.9 350000.0 4550 A Separation 8.4 500000.0 4636 The Other Dream Team 8.4 500000.0
2.2 通过排序选取每组的最大值——找到每年imdb评分最高的电影¶
- sort_values 按照年排序,ascending 升序排列
movie2 = movie[['movie_title', 'title_year', 'imdb_score']]
movie2.sort_values('title_year', ascending=False).head()
输出结果
movie_title title_year imdb_score 3884 The Veil 2016.0 4.7 2375 My Big Fat Greek Wedding 2 2016.0 6.1 2794 Miracles from Heaven 2016.0 6.8 92 Independence Day: Resurgence 2016.0 5.5 153 Kung Fu Panda 3 2016.0 7.2
- 同时对'title_year','imdb_score' 两列进行排序
movie3 = movie2.sort_values(['title_year','imdb_score'], ascending=False)
movie3.head()
输出结果
movie_title title_year imdb_score 4312 Kickboxer: Vengeance 2016.0 9.1 4277 A Beginner's Guide to Snuff 2016.0 8.7 3798 Airlift 2016.0 8.5 27 Captain America: Civil War 2016.0 8.2 98 Godzilla Resurgence 2016.0 8.2
- 用drop_duplicates去重,只保留每年的第一条数据
movie_top_year = movie3.drop_duplicates(subset='title_year')
movie_top_year.head()
输出结果
movie_title title_year imdb_score 4312 Kickboxer: Vengeance 2016.0 9.1 3745 Running Forever 2015.0 8.6 4369 Queen of the Mountains 2014.0 8.7 3935 Batman: The Dark Knight Returns, Part 2 2013.0 8.4 3 The Dark Knight Rises 2012.0 8.5
2.3 提取出每年,每种电影分级中预算少的电影——sort_values多列排序¶
- 多列排序时,ascending 参数传入一个列表,排序一一对应
movie4 = movie[['movie_title', 'title_year', 'content_rating', 'budget']]
# 多列排序,ascending=[False, False, True] 降序,降序,升序
movie4_sorted = movie4.sort_values(['title_year', 'content_rating', 'budget'], ascending=[False, False, True])
# 去重,删除'title_year', 'content_rating'相同的数据
movie4_sorted.drop_duplicates(subset=['title_year', 'content_rating']).head(10)
输出结果
movie_title title_year content_rating budget 4026 Compadres 2016.0 R 3000000.0 4658 Fight to the Finish 2016.0 PG-13 150000.0 4661 Rodeo Girl 2016.0 PG 500000.0 3252 The Wailing 2016.0 Not Rated NaN 4659 Alleluia! The Devil's Carnival 2016.0 NaN 500000.0 4731 Bizarre 2015.0 Unrated 500000.0 812 The Ridiculous 6 2015.0 TV-14 NaN 4831 The Gallows 2015.0 R 100000.0 4825 Romantic Schemer 2015.0 PG-13 125000.0 3796 R.L. Stine's Monsterville: The Cabinet of Souls 2015.0 PG 4400000.0
3 简单数据分析练习(租房数据)¶
- 载入数据
import pandas as pd
house_data = pd.read_csv('data/LJdata.csv')
- 把列名替换成英文
#查看原始列名
house_data.columns
输出结果
Index(['区域', '地址', '标题', '户型', '面积', '价格', '楼层', '建造时间', '朝向', '更新时间', '看房人数','备注', '链接地址'],dtype='object')
house_data.columns = ['district', 'address', 'title', 'house_type', 'area', 'price', 'floor', 'build_time', 'direction', 'update_time', 'view_num', 'extra_info', 'link']
- 查看数据基本情况
house_data.head()
输出结果
district address title house_type area price floor build_time direction update_time view_num extra_info link 0 燕莎租房 新源街 亮马桥 新源街 精装两居 交通便利 看房方便 随时入住 2室1厅 50平米 5800 中楼层(共6层) 1981年建板楼 南 2017.07.21 26 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101803342.html 1 望京租房 澳洲康都 澳洲康都东向精致两居室........... 2室1厅 79平米 7800 中楼层(共28层) 2005年建板塔结合 东 2017.07.23 33 距离14号线(东段)东湖渠站731米 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101753126.html 2 广安门租房 远见名苑 远见名苑 东向两居室 独立小区环境 适合居家 2室1厅 86平米 8000 低楼层(共25层) 2006年建塔楼 东 2017.07.20 34 距离7号线达官营站684米 随时看房 精装修 自供暖 https://bj.lianjia.com/zufang/101101756753.html 3 天通苑租房 天通苑北一区 北一区简装两居,采光好,视野美,出行方便 2室1厅 103平米 5300 低楼层(共13层) 2004年建板楼 东南 2017.07.25 30 距离5号线天通苑站927米 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101780034.html 4 团结湖租房 团结湖北口 团结湖北口近地铁高楼层朝南向精装修正规两居室 2室1厅 63平米 6400 高楼层(共16层) 1982年建塔楼 南 2017.07.26 30 距离10号线团结湖站88米 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101781083.html
house_data.info()
输出结果
<class 'pandas.core.frame.DataFrame'> RangeIndex: 2760 entries, 0 to 2759 Data columns (total 13 columns): district 2760 non-null object address 2760 non-null object title 2760 non-null object house_type 2760 non-null object area 2760 non-null object price 2760 non-null int64 floor 2760 non-null object build_time 2758 non-null object direction 2760 non-null object update_time 2760 non-null object view_num 2760 non-null int64 extra_info 2760 non-null object link 2760 non-null object dtypes: int64(2), object(11) memory usage: 280.4+ KB
house_data.shape
输出结果
(2760, 13)
house_data.describe()
输出结果
price view_num count 2760.000000 2760.000000 mean 7570.800725 13.448913 std 6316.204986 12.746202 min 1300.000000 0.000000 25% 4500.000000 4.000000 50% 6000.000000 10.000000 75% 8500.000000 19.000000 max 210000.000000 122.000000
- 找到租金最低,和租金最高的房子
house_data.loc[house_data['price']==210000]
house_data.loc[house_data['price']==1300]
house_data[house_data['price']==house_data['price'].min()]
house_data[house_data['price']==house_data['price'].max()]
- sort_values按照值排序 参数by 传入列名 参数 ascending(升序)
house_data.sort_values(by='price').head(1)
输出结果
district address title house_type area price floor build_time direction update_time view_num extra_info link 2527 良乡租房 伟业嘉园西里 半地下室 家电齐全 集中供暖 简单装修 1室1厅 46平米 1300 地下室(共5层) 2005年建 南 2017.07.19 14 随时看房 集中供暖
house_data.sort_values(by='price').tail(1)
输出结果
district address title house_type area price floor build_time direction update_time view_num extra_info link 2658 和平里租房 雍和家园二期 雍和家园 底商出租 使用面积720米 6室3厅 720平米 210000 低楼层(共6层) 2005年建板楼 南 2017.07.26 21 距离2号线雍和宫站293米 随时看房 集中供暖
- 找到最近新上的10套房源
house_data.sort_values(by='update_time', ascending=False).head(10)
输出结果
district address title house_type area price floor build_time direction update_time view_num extra_info link 347 劲松租房 武圣西里 武圣西里正规三居室,低楼层,看房方便 3室1厅 73平米 6500 低楼层(共6层) 1986年建板楼 东南 北 2017.07.27 0 距离10号线潘家园站965米 随时看房 https://bj.lianjia.com/zufang/101101862495.html 1790 广安门租房 恒昌花园 广安门恒昌花园西向三居室集中供暖 3室2厅 159平米 13500 高楼层(共28层) 1999年建塔楼 西 2017.07.27 12 距离7号线达官营站292米 随时看房 集中供暖 https://bj.lianjia.com/zufang/101101692254.html 2405 武夷花园租房 月亮城堡 月亮城堡精装修正规一居 南北通透 户型好 1室1厅 102平米 4500 低楼层(共11层) 2005年建板塔结合 南 北 2017.07.27 28 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101495373.html 2639 常营租房 北京像素南区 北京像素 地铁6号线草房 北向开间 1房间1卫 48平米 3750 低楼层(共23层) 2012年建板塔结合 北 2017.07.27 3 距离6号线草房站66米 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101852394.html 2366 马甸租房 北太平庄路 牡丹园精装一居室 可当两居 350米到10号线 南北通透 1室1厅 33平米 4000 低楼层(共5层) 1985年建板楼 南 2017.07.27 24 距离10号线牡丹园站335米 随时看房 精装修 集中供暖 https://bj.lianjia.com/zufang/101101622752.html
- 查看所有更新时间
#查看所有更新时间
house_data['update_time'].unique()
输出结果
array(['2017.07.21', '2017.07.23', '2017.07.20', '2017.07.25', '2017.07.26', '2017.07.16', '2017.07.22', '2017.07.24', '2017.07.27', '2017.07.19', '2017.07.14', '2017.07.15', '2017.07.17', '2017.07.18'], dtype=object)
- 看房人数
house_data['view_num'].mean() #平均值
house_data['view_num'].median() #中位数
# 通过describe()可以查看到
- 不同看房人数的房源数量,as_index = False 分组字段不作为行索引(默认为True)
tmp_df = house_data.groupby('view_num',as_index=False)['district'].count()
tmp_df.columns = ['view_num', 'count']
tmp_df.head()
输出结果
view_num count 0 0 152 1 1 149 2 2 143 3 3 129 4 4 147
- 画图 %matplotlib inline 功能是在jupyter notebook中内嵌绘图,并且可以省略掉 plt.show()
%matplotlib inline
tmp_df['count'].plot(kind='bar',figsize=(20,10))
输出结果
<matplotlib.axes._subplots.AxesSubplot at 0x14e1763fc88>
- 房租价格的分布
print(house_data['price'].mean()) #平均值
print(house_data['price'].std()) #标准差
print(house_data['price'].median()) #中位数
输出结果
7570.800724637681 6316.204986067457 6000.0
- 看房人数最多的朝向
popular_direction = house_data.groupby('direction',as_index=False)[['view_num']].sum()
popular_direction[popular_direction['view_num']==popular_direction['view_num'].max()]
输出结果
direction view_num 23 南 北 11785
- 房型分布情况
# 设置正常显示汉字和负号
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif'] = ['SimHei'] # 正常显示汉字
plt.rcParams['axes.unicode_minus'] = False # 正常显示负号
house_type_dis = house_data.groupby(['house_type']).count()
%matplotlib inline
house_type_dis['district'].plot(kind='bar') #柱状图
输出结果
<matplotlib.axes._subplots.AxesSubplot at 0x14e17db17b8>
- 最受欢迎的房型
tmp = house_data.groupby('house_type',as_index=False).agg({'view_num':'sum'})
tmp[tmp['view_num']==tmp['view_num'].max()]
输出结果
house_type view_num 5 2室1厅 17589
- 房子的平均租房价格 (元/平米)
house_data.loc[:,'price_per_m2'] = house_data['price']/house_data['area']
house_data['price_per_m2'].mean()
输出结果
87.72268429900454
- 热门小区
address_df = house_data[['address','view_num']].groupby(['address'],as_index=False).sum()
address_df.sort_values(by='view_num', ascending=False).head()
输出结果
address view_num 951 清芷园 246 369 卡布其诺 245 938 润枫水尚 217 1149 芍药居北里 194 743 新康园 186
- 出租房源最多的小区
tmp_df2 = house_data[['address','view_num']].groupby(['address'],as_index=False).count()
tmp_df2.columns = ['address','count']
tmp_df2.nlargest(columns='count', n=1)
输出结果
address count 1288 远洋山水 19
小结¶
- 掌握在Pandas中计算常用统计量的方法
- info 了解不同字段的条目数量,数据类型,是否缺失及内存占用情况
- describe 计算数值类型数据的常用统计量
- 熟练使用pandas进行简单排序、分组、聚合等计算
- nlargest 返回指定字段的前n个最大值
- nsmallest 返回指定字段的前n个最小值
- sort_values 指定字段,按值排序
- groupby 按字段分组
- agg 分组之后聚合