欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Pandas数据分析④——数据规整2(数据拼接/透视)

程序员文章站 2022-06-05 18:58:11
...

Pandas系列目录如下:
Pandas数据分析①——数据读取(CSV/TXT/JSON)
Pandas数据分析②——数据清洗(重复值/缺失值/异常值)
Pandas数据分析③——数据规整1(索引和列名调整/数据内容调整/排序)
Pandas数据分析⑤——数据分组与函数使用(Groupby/Agg/Apply/mean/sum/count)
Pandas数据分析⑥——数据分析实例(货品送达率与合格率/返修率/拒收率)
Pandas数据分析⑦——数据分析实例2(泰坦尼克号生存率分析)

数据规整是在数据清洗完毕后,将其调整成适合分析的结构,为后续的深入分析作准备,主要分为以下几类:

索引和列名调整: 设定新索引,筛选想要的列,更改列名
数据排序:根据索引或列进行排序
数据格式调整:更改数据类型,更改数据内容(去除空格标点符号/截取/替换/统一数据单位等),增加用于分析的辅助列
数据拼接:行堆叠和列拼接
数据透视:行或列维度转换

上一篇介绍前3种,本篇介绍后2种

一、数据拼接

1、行堆叠
① concat(objs, axis=0, join=‘outer’, join_axes=None, ignore_index=False,
keys=None, levels=None, names=None, verify_integrity=False,
copy=True)

参数说明:
objs: 拼接的series或dataframe
axis:拼接轴方向,默认为0,沿行拼接;若为1,沿列拼接
join:默认外联’outer’,拼接另一轴所有的label,缺失值用NaN填充;内联’inner’,只拼接另一轴相同的label;
join_axes: 指定需要拼接的轴的labels,可在join既不内联又不外联的时候使用
ignore_index:对index进行重新排序
keys:多重索引,便于区分来源表
sort: 按值排序
② Series 使用

s1 = pd.Series([0, 1], index=['a', 'b'])
s2 = pd.Series([2, 3, 4], index=['c', 'd', 'e'])
s3 = pd.Series([5, 6], index=['f', 'g'])
print(s1)
print(s2)
print(s3)
print(pd.concat([s1, s2, s3], axis=1))  # 沿着axis=1会有多列,没有指定join则默认outer

Pandas数据分析④——数据规整2(数据拼接/透视)

s4 = pd.concat([s1, s3])
print(s4)
print(pd.concat([s1, s4], axis=1, join='inner'))  # join只能inner\outer

Pandas数据分析④——数据规整2(数据拼接/透视)

print(pd.concat([s1, s4], axis=1, join_axes=[['a', 'c']])) # join_axes可以是一列或几列,仅保留join_axes的索引

Pandas数据分析④——数据规整2(数据拼接/透视)

print(pd.concat([s1, s2, s3], keys=['S1', 'S2', 'S3']))  # keys参数可以标注来源

Pandas数据分析④——数据规整2(数据拼接/透视)
③ Dataframe使用

df1 = pd.DataFrame(np.arange(6).reshape(3, 2), index=['a', 'b', 'c'],columns=['one', 'two'])
print(df1)
df2 = pd.DataFrame(5 + np.arange(4).reshape(2, 2), index=['a', 'c'],columns=['three', 'four'])
print(df2)
print(pd.concat([df1, df2], axis=1, keys=['level1', 'level2'],sort=True))   # print(pd.concat({'level1': df1, 'level2': df2}, axis=1, sort=True)) 效果一样

Pandas数据分析④——数据规整2(数据拼接/透视)

df1 = pd.DataFrame(np.random.randn(4, 3), columns=['a', 'b', 'c'])
df2 = pd.DataFrame(np.random.randn(2, 3), columns=['b', 'd', 'a'])
print(df1)
print(df2)
print(pd.concat([df1, df2],sort=True))  
print(pd.concat([df1,df2],axis=1,sort=True))  # 如果没有指定axis,则默认按行拼接,如果没有的列,就加在最后,补充为na

Pandas数据分析④——数据规整2(数据拼接/透视)

print(pd.concat([df1, df2], ignore_index=True,sort=True))  # concat就是把行拼接在一起,如果列没有的以NA值,忽略索引是会将被拼接的数组按从0开始的索引

Pandas数据分析④——数据规整2(数据拼接/透视)

pd.concat([df1, df2], ignore_index=True,sort=True,join='inner'))

Pandas数据分析④——数据规整2(数据拼接/透视)

print(pd.concat([df1, df2],axis=1,sort=True,join='inner',keys=['第一组','第二组']))

Pandas数据分析④——数据规整2(数据拼接/透视)

2、列拼接
① merge(left_data,right_data,on,left_on,right_on,suffixes,how,left_index,right_index)
参数说明:

left_data/right_data: 需要合并的两部分数据,左右顺序不同,结果有可能不一样,具体要结合how来看
on: 连接键,当两个表的连接键名一样,可以直接用on,而不用left_on和right_on,可以是单键或多键
left_on/right_on: 如果两个表键名不一样,则分别指出,可以是单键或多键
suffixes: 如果两边键名相同的,想要做区分,可以使用此参数指定区分格式,如suffixes=(’_left’, ‘_right’)
how:指定连接的方式,分为inner,left, right, outer,与SQL中的join一致,默认为Inner
left_index/right_index: 如果需要连接的键是索引,就不用left_on/right_on,而是用这两个,也可以一个用left_on,一个用right_index,两都可结合使用
使用

df1 = pd.DataFrame({'key': ['b', 'b', 'a', 'c', 'a', 'a', 'b'],
                     'data': range(7)})
df2 = pd.DataFrame({'key': ['a', 'b', 'd'],
                    'data': range(3)})
print(df1)
print(df2)

Pandas数据分析④——数据规整2(数据拼接/透视)Pandas数据分析④——数据规整2(数据拼接/透视)

print(pd.merge(df1, df2)) # 默认相同名字的键都作为连接键( key,data)
print(pd.merge(df1, df2, on='key')) # 通过On仅令key作为连接键

Pandas数据分析④——数据规整2(数据拼接/透视)

print(pd.merge(df1, df2, on='key', suffixes=('_left', '_right'), how='outer'))  # suffixes是如果左右有相同的,可以用_x和_y村明
print(pd.merge(df1, df2, on='key', suffixes=('_1', '_2'), how='left')) # 左连接是只要左边有就保留,右边如果没有就补充na,outer是两边的都要保留,匹配不出的就为Na

Pandas数据分析④——数据规整2(数据拼接/透视)

df1 = pd.DataFrame({'key1': ['b', 'b', 'a', 'c', 'a', 'a', 'b'],
                     'data1': range(7)})
df2 = pd.DataFrame({'key2': ['a', 'b', 'd'],
                    'data2': range(3)})
print(pd.merge(df1, df2, left_on='key1', right_on='key2', how='right'))
print(pd.merge(df1, df2, left_on='key1', right_on='key2', how='outer'))# 以左边的key1和右边的key2为连接键,两列一样都保留了

Pandas数据分析④——数据规整2(数据拼接/透视)

df1 = pd.DataFrame({'key1': ['b', 'b', 'a', 'c', 'a', 'a', 'b'],
                     'key2': range(7),
                     'data1': np.random.randn(7)})
df2 = pd.DataFrame({'key1': ['a', 'b', 'd'],
                    'key2': range(3),
                    'data2': np.random.randn(3)})
print(df1)
print(df2)
print(pd.merge(df1, df2, on=['key1', 'key2'], how='left'))  # on=[]可以是多个列 

Pandas数据分析④——数据规整2(数据拼接/透视)

df1 = pd.DataFrame({'key1': ['b', 'b', 'a', 'c', 'a', 'a', 'b'],
                     'key2': range(7),
                     'data1': np.random.randn(7)})
df2 = pd.DataFrame({'data2': np.random.randn(3)}, index=[['a', 'b', 'd'], [1, 2, 3]])
print(df1)
print(df2)
print(pd.merge(df1, df2, left_on=['key1', 'key2'], right_index=True,how='outer')) # left_on与right_index结合使用

Pandas数据分析④——数据规整2(数据拼接/透视)

 df1 = pd.DataFrame({'data1': np.random.randn(7)},index=[['b', 'b', 'a', 'c', 'a', 'a', 'b'],
                     [1,2,3,4,5,6,7]])
df2 = pd.DataFrame({'data2': np.random.randn(3)}, index=[['a', 'b', 'd'], [1, 2, 3]])
print(df1)
print(df2)
print(pd.merge(df1, df2, left_index=True, right_index=True,how='outer')) # 两边都是索引

Pandas数据分析④——数据规整2(数据拼接/透视)

二、数据透视

unstack/stack
unstack是拆堆,将行索引透视到列,如果没有的可以用Na补充,stack是将列透视到行,均可选择透视的字段

s1 = pd.Series([0, 1, 2], index=['a', 'b', 'c'])
s2 = pd.Series([4, 5], index=['d', 'e'])
data = pd.concat([s1, s2],keys=['one', 'two'])
print(data)

Pandas数据分析④——数据规整2(数据拼接/透视)

print(data.unstack(0))
print(data.unstack(0).stack())  # 如果有多层索引,可以用unstack()选择某个索引透视到行,如果有多个列索引,那也可以通过stack()选择哪个列透视到行

Pandas数据分析④——数据规整2(数据拼接/透视)

print(data.unstack().stack(dropna=False))  拆堆过程可能会产生Na,在stack()时可以选择dropna=False
print(data.unstack().stack())   # 如果不选择透视的先或列,unstack().stack()将恢复原样

Pandas数据分析④——数据规整2(数据拼接/透视)