プログラミング
記事内に商品プロモーションを含む場合があります

pandasのmergeによる表結合を深掘り解説(チートシート形式)

Aru

pandasを使ってデータを操作する場合、mergeやjoinを使った表の結合が行われます。機械学習やデータ分析では高い頻度で行う操作ですが、記述の方法を忘れやすいのでチートシート形式で整理しました。本記事では、pandasの操作のうち、mergeによる表結合に特化して解説します。

データの準備

この記事では以下の2つのデータフレームを利用します。

import pandas as pd


df0 = pd.DataFrame({'id': [1,2,3], 'age': [18, 20, 33], 'c': ['x', 'y', 'z']})
df1 = pd.DataFrame({'id': [1,2,4], 'Age': [18, 20, 33], 'c': ['x', 'm', 'n']})

print(df0)
#    id  age  c
# 0   1   18  x
# 1   2   20  y
# 2   3   33  z
print(df1)
#    id  Age  c
# 0   1   18  x
# 1   2   20  m
# 2   4   33  n

2つのデータフレームの内容は以下になります。

df0 ,df1の内容
df0の内容
インデックスidagec
0118x
1220y
2333z
df1の内容
インデックスidAgec
0118x
1220n
2433m

pandasのmerge()の使い方(基本)

基本(merge)

基本的な書き方です。pd.mergeには結合する2つのデータフレームを指定します

df = pd.merge(df0, df1)
print(df)
#    id  age c_x  Age c_y
# 0   1   18   x   18   x
# 1   2   20   y   20   m

2つの表の共通のものがマージされて、c列がc_x, c_yの2つで結合されます。

df0 ,df1の内容
df0の内容
インデックスidagec
0118x
1220y
2333z
df1の内容
インデックスidAgec
0118x
1220n
2433m

on : 結合するキーを指定(列を指定)

キーを指定(on)

onを使うことで、結合するキーを指定することが可能です。

onを省略しても良いですが、明示しておいた方が後々コードが読みやすいです

df = pd.merge(df0, df1, on='id')
print(df)
#    id  age c_x  Age c_y
# 0   1   18   x   18   x
# 1   2   20   y   20   m

idで結合していますが、結果は「基本」の例と同じです。

複数のキーを指定(on)

onには複数のキー列を指定することも可能です。複数キーを指定する場合は、列名をリスト形式で渡します。

df = pd.merge(df0, df1, on = ['id', 'c'])
print(df)
#    id  age  c  Age
# 0   1   18  x   18

例では、idc列をキーとして結合しています。idc列が同一なものは1つですので、結果は1行になります。

df0 ,df1の内容
df0の内容
インデックスidagec
0118x
1220y
2333z
df1の内容
インデックスidAgec
0118x
1220n
2433m

キーを指定(left_on, right_on)

2つの表の列名が異なっていても、left_on, right_onを指定することでキーとして結合することが可能です。

df = pd.merge(df0, df1, left_on = 'age', right_on = 'Age')
print(df)
#    id_x  age c_x  id_y  Age c_y
# 0     1   18   x     1   18   x
# 1     2   20   y     2   20   m
# 2     3   33   z     4   33   n

例では、df0のageとdf1のAgeの列をキーとして結合を行なっています。キーとして指定しなかった各列は_x, _yとして列が追加されます。

df0 ,df1の内容
df0の内容
インデックスidagec
0118x
1220y
2333z
df1の内容
インデックスidAgec
0118x
1220n
2433m

ageAgeは重複している情報なので、dropを使って片方を削除することが可能です。

列削除なので、drop(..., axis=1)とaxisをつける必要があります

df = pd.merge(df0, df1, left_on = 'age', right_on = 'Age').drop('Age', axis=1)
print(df)
#    id_x  age c_x  id_y c_y
# 0     1   18   x     1   x
# 1     2   20   y     2   m
# 2     3   33   z     4   n

how : 結合方法を指定

howを使って結合方法も指定することができます。デフォルトはinnerなので指定しないとinner結合されます。

inner

両方に共通する行が残ります

df = pd.merge(df0, df1, on='id', how = 'inner')
print(df)
#    id  age c_x  Age c_y
# 0   1   18   x   18   x
# 1   2   20   y   20   m

outer

両方の列が全て残ります。値がない部分にはNaNが挿入されます。

df = pd.merge(df0, df1, on='id', how = 'outer')
print(df)
#    id   age  c_x   Age  c_y
# 0   1  18.0    x  18.0    x
# 1   2  20.0    y  20.0    m
# 2   3  33.0    z   NaN  NaN
# 3   4   NaN  NaN  33.0    n

left(左結合)

左(mergeの先に書いたデータフレーム)を基準として結合します。右のデータフレームに存在しない行は、値をNaNにします。

ちなみに、私は、leftによる結合を結構行います

df = pd.merge(df0, df1, on='id', how = 'left')
print(df)
#    id  age c_x   Age  c_y
# 0   1   18   x  18.0    x
# 1   2   20   y  20.0    m
# 2   3   33   z   NaN  NaN

right(右結合)

右を基準にして結合します。leftと似たような動きです。

df = pd.merge(df0, df1, on='id', how = 'right')
print(df)
#    id   age  c_x  Age c_y
# 0   1  18.0    x   18   x
# 1   2  20.0    y   20   m
# 2   4   NaN  NaN   33   n

cross(交差結合)

全ての組み合わせを生成して結合します。

個人的には、あまり使う機会がありません

データが大きくなると組み合わせ爆発でメモリがなくなりますから使う機会は少ないです

df = pd.merge(df0, df1, how = 'cross')
print(df)

#    id_x  age c_x  id_y  Age c_y
# 0     1   18   x     1   18   x
# 1     1   18   x     2   20   m
# 2     1   18   x     4   33   n
# 3     2   20   y     1   18   x
# 4     2   20   y     2   20   m
# 5     2   20   y     4   33   n
# 6     3   33   z     1   18   x
# 7     3   33   z     2   20   m
# 8     3   33   z     4   33   n

indicator : 結合情報を追加

indicatorを設定することで、both, left_only, right_onlyの分類を追加することができます。

df = pd.merge(df0, df1, on='id', how = 'outer', indicator = True)
print(df)

#    id   age  c_x   Age  c_y      _merge
# 0   1  18.0    x  18.0    x        both
# 1   2  20.0    y  20.0    m        both
# 2   3  33.0    z   NaN  NaN   left_only
# 3   4   NaN  NaN  33.0    n  right_only

まとめ

結合にはjoinもありますが、似たような使い方です。個人的には、mergeの方が使いやすいのでここではmergeを説明しました。

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

ABOUT ME
ある/Aru
ある/Aru
IT&機械学習エンジニア/ファイナンシャルプランナー(CFP®)
専門分野は並列処理・画像処理・機械学習・ディープラーニング。プログラミング言語はC, C++, Go, Pythonを中心として色々利用。現在は、Kaggle, 競プロなどをしながら悠々自適に活動中
記事URLをコピーしました