- pandas で(
INNER
| (LEFT
|RIGHT
|FULL
)OUTER
)を実行するにはどうすればよいですか?JOIN
- マージ後に欠落した行に NaN を追加するにはどうすればよいですか?
- マージ後に NaN を取り除くにはどうすればいいですか?
- インデックスをマージできますか?
- 複数の DataFrame をマージするにはどうすればよいですか?
- パンダとのクロス結合
merge
?join
?concat
?update
誰? 何? なぜ?!
...などなど。私は、パンダのマージ機能のさまざまな側面について尋ねるこれらの質問が繰り返し寄せられているのを見てきました。現在、マージとそのさまざまな使用例に関する情報のほとんどは、不適切な表現で検索できない数十の投稿に分散しています。ここでの目的は、後世のために、より重要な点のいくつかをまとめることです。
このQ&Aは、一般的なパンダのイディオムに関する役立つユーザーガイドシリーズの次の記事となる予定です(ピボットに関するこの投稿、 そして連結に関するこの投稿(これについては後ほど触れます)。
この投稿は、ドキュメントですので、ぜひそちらも読んでみてください。いくつかの例はそこから引用しています。
目次
アクセスを容易にするため。
マージの基本 - 結合の基本タイプ(まずこれを読んでください)
ベストアンサー1
この投稿の目的は、Pandas を使用した SQL 風のマージ、その使用方法、使用すべきでないケースについて読者に入門書を提供することです。
具体的には、この投稿で取り上げる内容は次のとおりです。
基本 - 結合の種類 (LEFT、RIGHT、OUTER、INNER)
- 異なる列名との結合
- 複数の列を結合する
- 出力でマージキー列が重複しないようにする
この投稿 (およびこのスレッドでの私の他の投稿) では、次のことが実行されません。
- パフォーマンス関連の議論とタイミング (現時点では)。適切な場合は、主に、より優れた代替案について言及します。
- サフィックスの処理、余分な列の削除、出力の名前変更、その他の特定のユースケース。これについては他の (つまり、より優れた) 投稿で取り上げられているので、ぜひ理解してください。
注:特に指定がない限り、ほとんどの例ではさまざまな機能を説明する際にデフォルトで INNER JOIN 操作が使用されます。
さらに、ここにあるすべてのデータフレームはコピーして複製できるので、自由に操作できます。また、この郵便受けクリップボードから DataFrame を読み取る方法について説明します。
最後に、JOIN操作の視覚的表現はすべてGoogle Drawingsを使用して手描きされています。ここ。
話はもう十分です。使い方を教えてくださいmerge
。
セットアップと基本
np.random.seed(0)
left = pd.DataFrame({'key': ['A', 'B', 'C', 'D'], 'value': np.random.randn(4)})
right = pd.DataFrame({'key': ['B', 'D', 'E', 'F'], 'value': np.random.randn(4)})
left
key value
0 A 1.764052
1 B 0.400157
2 C 0.978738
3 D 2.240893
right
key value
0 B 1.867558
1 D -0.977278
2 E 0.950088
3 F -0.151357
簡潔にするために、キー列の名前は同じです (現時点では)。
INNER JOINは次のように表されます。
注:この図と今後の図はすべて次の規則に従います。
- 青はマージ結果に存在する行を示します
- 赤は結果から除外された行(つまり削除された行)を示します。
- 緑は
NaN
結果でsに置き換えられた欠損値を示します
INNER JOINを実行するには、merge
左側の DataFrame で、右側の DataFrame と結合キー (少なくとも) を引数として指定します。
left.merge(right, on='key')
# Or, if you want to be explicit
# left.merge(right, on='key', how='inner')
key value_x value_y
0 B 0.400157 1.867558
1 D 2.240893 -0.977278
これは、共通キーを共有する および の行のみを返します (この例では、「B」と「D」left
) 。right
LEFT OUTER JOIN、またはLEFT JOINは次のように表されます。
これは を指定することによって実行できますhow='left'
。
left.merge(right, on='key', how='left')
key value_x value_y
0 A 1.764052 NaN
1 B 0.400157 1.867558
2 C 0.978738 NaN
3 D 2.240893 -0.977278
ここで NaN の配置に注意してください。 を指定した場合how='left'
、 のキーのみleft
が使用され、 の欠落データはright
NaN に置き換えられます。
同様に、RIGHT OUTER JOIN、つまり RIGHT JOIN の場合も...
...特定how='right'
:
left.merge(right, on='key', how='right')
key value_x value_y
0 B 0.400157 1.867558
1 D 2.240893 -0.977278
2 E NaN 0.950088
3 F NaN -0.151357
ここでは、 からのキーright
が使用され、 からの欠落データはleft
NaN に置き換えられます。
最後に、FULL OUTER JOINの場合、
特定how='outer'
。
left.merge(right, on='key', how='outer')
key value_x value_y
0 A 1.764052 NaN
1 B 0.400157 1.867558
2 C 0.978738 NaN
3 D 2.240893 -0.977278
4 E NaN 0.950088
5 F NaN -0.151357
これは両方のフレームのキーを使用し、両方の欠落行に NaN が挿入されます。
ドキュメントでは、これらのさまざまなマージがわかりやすくまとめられています。
その他の結合 - 左除外、右除外、および完全除外/反対結合
2 つの手順でLEFT-Excluding JOINとRIGHT-Excluding JOIN が必要な場合。
LEFT除外結合の場合は次のように表される。
まずLEFT OUTER JOINを実行し、右側の行のみをフィルタリングしますleft
(右側の行はすべて除外します)。
(left.merge(right, on='key', how='left', indicator=True)
.query('_merge == "left_only"')
.drop('_merge', 1))
key value_x value_y
0 A 1.764052 NaN
2 C 0.978738 NaN
どこ、
left.merge(right, on='key', how='left', indicator=True)
key value_x value_y _merge
0 A 1.764052 NaN left_only
1 B 0.400157 1.867558 both
2 C 0.978738 NaN left_only
3 D 2.240893 -0.977278 both
同様に、RIGHT-Excluding JOINの場合、
(left.merge(right, on='key', how='right', indicator=True)
.query('_merge == "right_only"')
.drop('_merge', 1))
key value_x value_y
2 E NaN 0.950088
3 F NaN -0.151357
最後に、左または右のキーのみを保持するマージを実行する必要がある場合(つまり、ANTI-JOINを実行する場合)、
同様の方法でこれを行うことができます。
(left.merge(right, on='key', how='outer', indicator=True)
.query('_merge != "both"')
.drop('_merge', 1))
key value_x value_y
0 A 1.764052 NaN
2 C 0.978738 NaN
4 E NaN 0.950088
5 F NaN -0.151357
キー列の異なる名前
キー列の名前が異なる場合(たとえば、ではなく がleft
ありkeyLeft
、がright
ある場合)は、ではなく とを引数として指定する必要があります。keyRight
key
left_on
right_on
on
left2 = left.rename({'key':'keyLeft'}, axis=1)
right2 = right.rename({'key':'keyRight'}, axis=1)
left2
keyLeft value
0 A 1.764052
1 B 0.400157
2 C 0.978738
3 D 2.240893
right2
keyRight value
0 B 1.867558
1 D -0.977278
2 E 0.950088
3 F -0.151357
left2.merge(right2, left_on='keyLeft', right_on='keyRight', how='inner')
keyLeft value_x keyRight value_y
0 B 0.400157 B 1.867558
1 D 2.240893 D -0.977278
出力で重複するキー列を回避する
keyLeft
から およびleft
からkeyRight
をマージするときに、出力にまたは のいずれか(両方ではない)right
のみが必要な場合は、予備的な手順としてインデックスを設定することから始めることができます。keyLeft
keyRight
left3 = left2.set_index('keyLeft')
left3.merge(right2, left_index=True, right_on='keyRight')
value_x keyRight value_y
0 0.400157 B 1.867558
1 2.240893 D -0.977278
これを直前のコマンドの出力 (つまり、 の出力left2.merge(right2, left_on='keyLeft', right_on='keyRight', how='inner')
) と比較すると、keyLeft
が欠落していることがわかります。どのフレームのインデックスがキーとして設定されているかに基づいて、どの列を保持するかがわかります。これは、たとえば OUTER JOIN 操作を実行するときに重要になることがあります。
1つの列のみを結合するDataFrames
例えば、
right3 = right.assign(newcol=np.arange(len(right)))
right3
key value newcol
0 B 1.867558 0
1 D -0.977278 1
2 E 0.950088 2
3 F -0.151357 3
「newcol」のみをマージする必要がある場合(他の列はマージしない)、通常はマージする前に列をサブセット化することができます。
left.merge(right3[['key', 'newcol']], on='key')
key value newcol
0 B 0.400157 0
1 D 2.240893 1
LEFT OUTER JOIN を実行する場合、よりパフォーマンスの高いソリューションは次のようになりますmap
。
# left['newcol'] = left['key'].map(right3.set_index('key')['newcol']))
left.assign(newcol=left['key'].map(right3.set_index('key')['newcol']))
key value newcol
0 A 1.764052 NaN
1 B 0.400157 0.0
2 C 0.978738 NaN
3 D 2.240893 1.0
前述のように、これはに似ていますが、より高速です。
left.merge(right3[['key', 'newcol']], on='key', how='left')
key value newcol
0 A 1.764052 NaN
1 B 0.400157 0.0
2 C 0.978738 NaN
3 D 2.240893 1.0
複数の列を結合する
複数の列を結合するには、 のリストon
(またはleft_on
必要right_on
に応じて と ) を指定します。
left.merge(right, on=['key1', 'key2'] ...)
または、名前が異なる場合は、
left.merge(right, left_on=['lkey1', 'lkey2'], right_on=['rkey1', 'rkey2'])
その他の便利なmerge*
操作と機能
インデックスでデータフレームとシリーズをマージする: 参照この答え。
その上
merge
、DataFrame.update
そしてDataFrame.combine_first
特定のケースでは、ある DataFrame を別の DataFrame に更新するために使用されます。pd.merge_ordered
順序付き JOIN に便利な関数です。pd.merge_asof
(読み取り: merge_asOf) は近似結合に役立ちます。
このセクションでは、基本的な内容のみを取り上げ、読者の興味をそそることを目的としています。その他の例やケースについては、merge
、、join
およびに関するドキュメントconcat
関数仕様へのリンクもあります。
読み続けて
学習を続けるには、Pandas Merging 101 の他のトピックにジャンプしてください。
*あなたはここにいる。