Pandas 中的数据拼接操作详解

numpy的级联回顾

import numpy as np
import pandas as pd
from pandas import DataFrame, Series

n1 = np.random.randint(0, 10, size=(3, 3))
n2 = np.random.randint(0, 10, size=(3, 3))
display(n1, n2)

"""
array([[4, 1, 0],
       [7, 1, 4],
       [8, 6, 1]])
       
array([[7, 9, 9],
       [6, 5, 1],
       [5, 2, 2]])
"""

# axis=0拼接
np.concatenate((n1, n2))
# 快捷写法
np.vstack((n1, n2))

"""
array([[0, 5, 9],
       [7, 3, 2],
       [0, 9, 7],
       [2, 2, 5],
       [2, 0, 9],
       [9, 4, 8]])
"""

# axis=0, 水平方向拼接
np.concatenate((n1, n2), axis=1)
# 快捷写法
np.hstack((n1, n2))
"""
array([[8, 7, 5, 0, 2, 0],
       [7, 0, 3, 5, 1, 7],
       [4, 1, 3, 0, 5, 4]])
"""

pd.concat()级联

  • objs:这是一个要连接的 Pandas 对象的序列,可以是 Series、DataFrame 或 Panel 对象。

  • axis:默认为 0,表示沿着行的方向拼接,设为 1 则表示沿着列的方向拼接。

  • join:指定如何处理其他轴上的索引。可选值包括 inner(交集)、outer(并集)、left(保留左侧索引)、right(保留右侧索引)。默认为 outer。

  • ignore_index:如果设置为 True,则忽略原始对象的索引并生成一个新的整数索引。默认为 False。

  • keys:用于创建层次化索引的值,可用于标识拼接前不同数据块来源。可以是单个值或序列,默认为 None。

  • levels:用于创建 MultiIndex 的层次化索引级别。默认为 None。

  • names:用于设置创建的 MultiIndex 索引级别的名称。默认为 None。

  • verify_integrity:如果设置为 True,则在拼接操作之前会检查新的轴上是否有重复索引。如果发现重复索引,会抛出异常。默认为 False。

  • sort:在拼接轴上的索引排序。默认为 False。

  • copy:如果设置为 False,则在可能的情况下,返回的对象不会复制。默认为 True。

index = ['悟空', '悟饭', '悟天']
columns = ['语文', '数学', '英语']
data = np.random.randint(0, 150, size=(3, 3))
df1 = DataFrame(index=index, columns=columns, data=data)

data = np.random.randint(0, 150, size=(3, 3))
df2 = DataFrame(index=index, columns=columns, data=data)
display(df1, df2)
语文数学英语
悟空732784
悟饭1262684
悟天33029
语文数学英语
悟空345229
悟饭1362985
悟天319121
# 默认是axis=0, 即垂直方向
pd.concat((df1, df2))
语文数学英语
悟空732784
悟饭1262684
悟天33029
悟空345229
悟饭1362985
悟天319121
# dataframe最好不要有相同的索引. 索引最好唯一. 
# axis=1,水平直连; ignore_index重置索引
pd.concat((df1, df2), axis=1, ignore_index=True)
012345
悟空732784345229
悟饭12626841362985
悟天33029319121
# 可以通过keys, 保留原来的索引. 多加一层索引来加以区分. 
pd.concat((df1, df2), axis=1, keys=['df1', 'df2'])
df1df2
语文数学英语语文数学英语
悟空732784345229
悟饭12626841362985
悟天33029319121
# verify_integrity=True之后不允许出现重复的索引. 
# pd.concat((df1, df2), verify_integrity=True) # 异常! 索引你重复

索引不匹配级联

index2 = ['悟空', '悟饭', '武神']

data = np.random.randint(0, 150, size=(3, 3))
df2 = DataFrame(index=index2, columns=columns, data=data)
display(df1, df2)
语文数学英语
悟空732784
悟饭1262684
悟天33029
语文数学英语
悟空3710092
悟饭343947
武神1210151
# 不匹配级联: 会自动把索引相同的位置进行级联, 索引不同的位置, 补NaN
pd.concat((df1, df2), axis=1)
语文数学英语语文数学英语
悟空73.027.084.037.0100.092.0
悟饭126.026.084.034.039.047.0
悟天3.030.029.0NaNNaNNaN
武神NaNNaNNaN12.0101.051.0
# 默认是外连接join='outer'; 
# join='inner' 内连接:只显示匹配的项
pd.concat((df1, df2), axis=1, join='inner')
语文数学英语语文数学英语
悟空7327843710092
悟饭1262684343947

使用append()函数添加

专门用于在后面添加

# append是dataframe对象的方法
# append就是axis=0
df1.append(df2, ignore_index=True)

pd.merge()合并

  • how:指定如何执行合并操作。可选值包括:
    inner:取两个 DataFrame 的交集,即只保留两者共有的部分。
    outer:取两个 DataFrame 的并集,即保留所有数据。
    left:基于左侧 DataFrame 的键进行合并。
    right:基于右侧 DataFrame 的键进行合并。

  • on:指定用于合并的列名。如果左右两个 DataFrame 中的列名不同,可以分别指定左右两个 DataFrame 中用于合并的列名。

  • left_on:左侧 DataFrame 中用于合并的列名。

  • right_on:右侧 DataFrame 中用于合并的列名。

  • left_index:如果为 True,则使用左侧 DataFrame 的索引作为合并键。

  • right_index:如果为 True,则使用右侧 DataFrame 的索引作为合并键。

  • suffixes:如果列名冲突,可以指定添加到列名末尾的后缀,以区分这些列来自哪个 DataFrame。

  • indicator:如果设置为 True,在结果 DataFrame 中添加一个特殊的列,指示每行的合并方式(如是来自左表、右表还是两者的交集)。

  • validate:用于检查合并操作的有效性。可选值包括 one_to_one、one_to_many、many_to_one、many_to_many。

  • sort:如果为 True,在执行合并操作前对合并键进行排序

merge与concat的区别
merge需要依据某一共同列来进行合并,会自动根据两者相同column名称的那一列,作为key来进行合并。

# 创建两个示例 DataFrame
df1 = pd.DataFrame({'key': ['A', 'B', 'C', 'D'],
                    'value': [1, 2, 3, 4]})
df2 = pd.DataFrame({'key': ['B', 'D', 'E', 'F'],
                    'value': [5, 6, 7, 8]})
display(df1, df2)
keyvalue
0A1
1B2
2C3
3D4
keyvalue
0B5
1D6
2E7
3F8
# how='outer'取两个 DataFrame 的并集; on=key指定合并的列名
pd.merge(df1, df2, how='outer', on='key')
keyvalue_xvalue_y
0A1.0NaN
1B2.05.0
2C3.0NaN
3D4.06.0
4ENaN7.0
5FNaN8.0
# 设置key作为索引
df1.set_index('key', inplace=True)
df2.set_index('key', inplace=True)

# 使用key作为索引进行合并
# suffixes指定添加到列名末尾的后缀; 解决列名冲突
df = pd.merge(df1, df2, how='inner', left_index=True, right_index=True, 
              suffixes=('_left', '_right'))
df
value_leftvalue_right
key
B25
D46
# indicator=True;添加一个特殊的列,指示每行的合并方式来源
res = pd.merge(df1, df2, how='outer', on='key', indicator=True)
res
value_xvalue_y_merge
key
A1.0NaNleft_only
B2.05.0both
C3.0NaNleft_only
D4.06.0both
ENaN7.0right_only
FNaN8.0right_only
# left_on和right_on参数示例
df3 = pd.DataFrame({'key_left': ['A', 'B', 'C', 'D'],
                    'value_left': [1, 2, 3, 4]})
df4 = pd.DataFrame({'key_right': ['B', 'D', 'E', 'F'],
                    'value_right': [5, 6, 7, 8]})
display(df3, df4)

# how='inner'求交集; df3根据key_left, df4根据key_right进行合并
res = pd.merge(df3, df4, how='inner', left_on='key_left', right_on='key_right')
res
key_leftvalue_left
0A1
1B2
2C3
3D4
key_rightvalue_right
0B5
1D6
2E7
3F8
key_leftvalue_leftkey_rightvalue_right
0B2B5
1D4D6
  • 21
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值