文章目录
- 一. 连接数据
- 1.简介
- 2. 加载数据
- 1. 添加行
- ① 添加行-DataFrame连接
- ② 添加行-DataFrame和Series连接
- ③ 添加行-append函数
- ④ 添加行-重置索引
- 2. 添加列
- ① 添加列-concat函数
- ② 添加列-通过dataframe['列名'] = ['值']
- ③ 添加列-通过dataframe['列名'] = Series对象
- ④ 添加列-重置索引
- 3. 合并多个数据集
- ① 简介
- ② 加载数据
- ③ merge()合并
- Ⅰ. 一对一合并
- Ⅱ. 多对一合并
- ④ join()合并
- Ⅰ. 加载数据
- Ⅱ.依据两个DataFrame的行索引
- Ⅲ.将两个DataFrame的Symbol设置为行索引,再次join数据
- Ⅳ.将一个DataFrame的Symbol列设置为行索引,与另一个DataFrame的Symbol列进行join
一. 连接数据
1.简介
- 数据清理
- 在动手进行数据分析工作之前,需要进行数据清理工作 每个观测值成一行 每个变量成一列 每种观测单元构成一张表格
- 数据整理好之后,可能需要多张表格组合到一起才能进行某些问题的分析 一张表保存公司名称,另一张表保存股票价格 单个数据集也可能会分割成多个,比如时间序列数据,每个日期可能在一个单独的文件中
- 连接介绍
组合数据的一种方法是使用“连接”(concatenation)
连接是指把某行或某列追加到数据中
数据被分成了多份可以使用连接把数据拼接起来
把计算的结果追加到现有数据集,可以使用连接
2. 加载数据
import pandas as pd
df1 = pd.read_csv('data/concat_1.csv')
df2 = pd.read_csv('data/concat_2.csv')
df3 = pd.read_csv('data/concat_3.csv')
1. 添加行
① 添加行-DataFrame连接
-
可以使用concat函数将上面3个DataFrame连接起来
# 需将3个DataFrame放到同一个列表中 row_concat = pd.concat([df1, df2,df3]) row_concat
-
通过 iloc ,loc等方法取出连接后的数据的子集
row_concat.iloc[3,]
row_concat.loc[3,]
② 添加行-DataFrame和Series连接
-
使用concat连接DataFrame和Series
new_series = pd.Series(['n1', 'n2', 'n3', 'n4']) new_series
pd.concat([df1,new_series])
由于Series是列数据,concat方法默认是添加行,但是Series数据没有行索引,
所以添加了一个新列,缺失的数据用NaN填充
NaN是Python用于表示“缺失值”的方法 -
如果想将[‘n1’,‘n2’,‘n3’,‘n4’]作为行连接到df1后,可以创建DataFrame并指定列名
new_series2 = pd.DataFrame([['n1', 'n2', 'n3', 'n4']],columns=['A', 'B', 'C', 'D']) new_series2
pd.concat([df1,new_series2])
pd.concat([df1,new_series2],axis=1)
③ 添加行-append函数
-
concat可以连接多个对象,如果只需要向现有DataFrame追加一个对象,可以通过append函数来实现
df1.append(df2)
df1.append(new_series)
-
使用Python字典添加数据行
DataFrame中append一个字典的时候,必须传入ignore_index = Truedata_dict = {'A':'n1','B':'n2','C':'n3','D':'n4'} df1.append(data_dict,ignore_index=True)
④ 添加行-重置索引
- 如果是两个或者多个DataFrame连接,可以通过ignore_index = True参数,忽略后面DataFrame的索引
pd.concat([df1,df2,df3],ignore_index=True)
2. 添加列
① 添加列-concat函数
使用concat函数添加列,与添加行的方法类似
需要多传一个axis参数 axis的默认值是index 按行添加,传入参数 axis = columns 即可按列添加
pd.concat([df1,df2,df3],axis = 1)
通过列名获取子集
col_concat = pd.concat([df1,df2,df3],axis = 1)
col_concat['A']
② 添加列-通过dataframe[‘列名’] = [‘值’]
向DataFrame添加一列,不需要调用函数,通过dataframe[‘列名’] = [‘值’] 即可
col_concat['new_col'] = ['n1', 'n2', 'n3', 'n4']
col_concat
③ 添加列-通过dataframe[‘列名’] = Series对象
通过dataframe[‘列名’] = Series对象 这种方式添加一列\
col_concat['new_col_series'] = pd.Series(['n1', 'n2', 'n3', 'n4'])
col_concat
④ 添加列-重置索引
pd.concat([df1,df2,df3],axis = 'columns',ignore_index=True)
3. 合并多个数据集
① 简介
- 在使用concat连接数据时,涉及到了参数join(join = ‘inner’,join = ‘outer’)
- 数据库中可以依据共有数据把两个或者多个数据表组合起来,即join操作
- DataFrame 也可以实现类似数据库的join操作
- Pandas可以通过pd.join命令组合数据,也可以通过pd.merge命令组合数据
- merge更灵活,如果想依据行索引来合并DataFrame可以考虑使用join函数
② 加载数据
从数据库加载数据
import sqlite3
con = sqlite3.connect('data/chinook.db')
tracks = pd.read_sql_query("SELECT * FROM tracks", con)
tracks.head()
从数据库中读取表,第一个参数是表名,第二个参数是数据库连接对象
genres = pd.read_sql_query("SELECT * FROM genres",con)
genres.head()
③ merge()合并
Ⅰ. 一对一合并
最简单的合并只涉及两个DataFrame——把一列与另一列连接,且要连接的列不含任何重复值
-
先从tracks中提取部分数据,使其不含重复的’GenreId’值
tracks_subset = tracks.loc[[0,62,76,98,110,193,204,281,322,359],] tracks_subset
-
通过’GenreId’列合并数据,how参数指定连接方式
how = ’left‘ 对应SQL中的 left outer 保留左侧表中的所有key
how = ’right‘ 对应SQL中的 right outer 保留右侧表中的所有key
how = ‘outer’ 对应SQL中的 full outer 保留左右两侧侧表中的所有key
how = ‘inner’ 对应SQL中的 inner 只保留左右两侧都有的key -
left
genre_track = genres.merge(tracks_subset[['TrackId','GenreId','Milliseconds']],on='GenreId',how='left') genre_track
-
right
genre_track = genres.merge(tracks_subset[['TrackId','GenreId','Milliseconds']],on='GenreId',how='right') genre_track
Ⅱ. 多对一合并
-
使用tracks的全部数据
genre_track = genres.merge(tracks[['TrackId','GenreId','Milliseconds']],on='GenreId',how='left') genre_track
-
转换时间单位
如上面结果所示,Name的值在合并后的数据中被复制了
计算每种类型音乐的平均时长
to_timedelta 将Milliseconds列转变为timedelta数据类型
参数unit=‘ms’ 时间单位
dt.floor(‘s’) dt.floor() 时间类型数据,按指定单位截断数据genre_time = genre_track.groupby('Name')['Milliseconds'].mean() pd.to_timedelta(genre_time, unit='ms').dt.floor('s').sort_values()
-
计算每名用户的平均消费
从三张表中获取数据,用户表获取用户id,姓名
发票表,获取发票id,用户id
发票详情表,获取发票id,单价,数量
-
根据用户Id(‘CustomerId’)合并用户表和发票表,根据发票Id (‘InvoiceId’)合并发票和发票详情表
cust_inv = cust.merge(invoice,on='CustomerId').merge(ii,on='InvoiceId') cust_inv.head()
-
计算用户每笔消费的总金额
DataFrame的assign方法 创建新列total = cust_inv['Quantity']*cust_inv['UnitPrice'] cust_inv = cust_inv.assign(Total=total) cust_inv.head()
-
计算每名用户的平均消费
按照用户Id,姓名分组,分组后对总金额求和,并排序cols = ['CustomerId','FirstName','LastName'] cust_inv.groupby(cols)['Total'].sum().sort_values(ascending=False).head()
④ join()合并
使用join合并,可以是依据两个DataFrame的行索引,
或者一个DataFrame的行索引另一个DataFrame的列索引进行数据合并
Ⅰ. 加载数据
stocks_2016 = pd.read_csv('data/stocks_2016.csv')
stocks_2017 = pd.read_csv('data/stocks_2017.csv')
stocks_2018 = pd.read_csv('data/stocks_2018.csv')
Ⅱ.依据两个DataFrame的行索引
如果合并的两个数据有相同的列名,需要通过lsuffix,和rsuffix,指定合并后的列名的后缀
stocks_2016.join(stocks_2017, lsuffix='_2016', rsuffix='_2017', how='outer')
Ⅲ.将两个DataFrame的Symbol设置为行索引,再次join数据
stocks_2016.set_index('Symbol').join(stocks_2018.set_index('Symbol'),lsuffix='_2016', rsuffix='_2018')
Ⅳ.将一个DataFrame的Symbol列设置为行索引,与另一个DataFrame的Symbol列进行join
stocks_2016.join(stocks_2018.set_index('Symbol'),lsuffix='_2016', rsuffix='_2018',on='Symbol')