merge ใน pandas คือวิธีที่ผมใช้รวมสองตารางเข้าด้วยกันโดยจับคู่ตามคอลัมน์ที่กำหนด เหมือน VLOOKUP ใน Excel แต่ทรงพลังกว่ามากเพราะดึงได้ทุกคอลัมน์และรองรับ join หลายรูปแบบในคำสั่งเดียวครับ
pd.merge(left, right, on, how, left_on, right_on)
pd.merge(left, right, on, how, left_on, right_on)
DataFrame
คืนเป็น DataFrame ใหม่ที่รวมคอลัมน์จากทั้งสองตารางไว้ด้วยกันครับ ไม่แก้ไขตารางต้นฉบับ (left/right ยังอยู่เหมือนเดิม) สามารถ chain ต่อได้ทันทีเช่น .dropna() หรือ .reset_index()
| Argument | Type | Required | Default | Description |
|---|---|---|---|---|
| left | DataFrame | Yes | ตารางซ้าย — ตารางหลักที่เป็นฐาน | |
| right | DataFrame | Yes | ตารางขวา — ตารางที่จะนำมาเสริมข้อมูลให้ตารางซ้าย | |
| on | str | list | Optional | ชื่อคอลัมน์ที่ใช้จับคู่ (ต้องมีอยู่ในทั้งสองตาราง) เช่น on=’id’ หรือ on=[‘year’,’month’] | |
| how | str | Optional | 'inner' | รูปแบบ join: ‘inner’ (เฉพาะที่จับคู่ได้), ‘left’ (รักษาซ้ายทั้งหมด), ‘right’ (รักษาขวาทั้งหมด), ‘outer’ (เอาทุกแถวจากทั้งสองตาราง) |
| left_on | str | list | Optional | ชื่อคอลัมน์ฝั่งซ้ายที่ใช้จับคู่ ใช้คู่กับ right_on เมื่อคอลัมน์ key มีชื่อต่างกันสองตาราง | |
| right_on | str | list | Optional | ชื่อคอลัมน์ฝั่งขวาที่ใช้จับคู่ ใช้คู่กับ left_on เมื่อคอลัมน์ key มีชื่อต่างกันสองตาราง |
pd.merge(left, right, on='product_id')pd.merge(left, right, on='product_id')
order_id product_id qty product_name price
0 1 101 5 Apple 10
1 2 102 3 Banana 5
2 3 103 2 Cherry 20
pd.merge(left, right, on='product_id', how='left')pd.merge(left, right, on='product_id', how='left')
order_id product_id qty product_name price
0 1 101 5 Apple 10.0
1 2 102 3 Banana 5.0
2 3 103 2 Cherry 20.0
3 4 104 1 NaN NaN
pd.merge(left, right, on=['year', 'month'], how='left')pd.merge(left, right, on=['year', 'month'], how='left')
year month sales target
0 2023 1 100 120.0
1 2023 2 200 180.0
2 2024 1 150 160.0
3 2024 2 250 NaN
pd.merge(left, right, left_on='cust_id', right_on='customer_id')pd.merge(left, right, left_on='cust_id', right_on='customer_id')
order_id cust_id amount customer_id customer_name
0 1 10 500 10 Alice
1 2 11 300 11 Bob
2 3 10 700 10 Alice
ต่างกันหลักๆ ที่ทิศทางครับ concat ต่อแถวหรือคอลัมน์โดยไม่ต้องจับคู่ — เอาตาราง A กับ B มาวางต่อกัน เหมือน Ctrl+V ใน Excel merge ต่างกันตรงที่ต้องมี key ร่วม แล้วมันจะจับคู่แถวให้ เหมาะกับงาน “เพิ่มข้อมูลจากอีกตารางโดยอิงตามรหัสร่วมกัน” ครับ
pandas จะ expand ออกครับ เช่น order_id 1 ตารางซ้ายกับ product_id 101 ตารางขวาที่มี 2 แถว — ผลลัพธ์จะได้ 2 แถวสำหรับ order_id 1 เลย เหมือนการ cartesian join ในส่วนนั้น ผมเจอปัญหานี้บ่อยตอน data ไม่ clean ครับ ถ้าไม่ต้องการผลแบบนี้ต้อง deduplicate ตารางขวาก่อน merge
เพราะ pandas เก็บทั้งสองไว้ให้ครับ ตัวมันเองไม่รู้ว่าเราอยากได้อันไหน ผมมักจะ drop อันที่ redundant ต่อท้ายด้วย .drop(columns=[‘customer_id’]) เพื่อให้ DataFrame สะอาดขึ้น หรือบางทีก็ rename ไปเลยตามต้องการ
ถ้าผมจะอธิบาย merge ให้เข้าใจเร็วที่สุด คือมันคือ “VLOOKUP ที่ทำได้ถูกต้องตั้งแต่แรก” — แทนที่จะดึงทีละคอลัมน์ด้วย VLOOKUP/XLOOKUP ใน Excel, merge รวมทั้งตารางซ้ายและขวาเข้าหากันโดยจับคู่ตาม key ที่กำหนด แล้วคืนออกมาเป็น DataFrame ใหม่ที่มีทุกคอลัมน์ของทั้งสองตารางพร้อมกันครับ
สอนแบบ 3 จังหวะให้จำง่ายนะครับ:
– จังหวะที่ 1 **Left + Right**: เลือกสองตารางที่จะรวม — ตารางซ้ายคือฐาน ตารางขวาคือแหล่งข้อมูลที่จะดึงมาเสริม
– จังหวะที่ 2 **on= / left_on= + right_on=**: บอกว่าจับคู่ด้วยคอลัมน์อะไร ถ้าชื่อเหมือนกันทั้งสองตารางใช้ on= อย่างเดียว ถ้าชื่อต่างกันต้องบอกทั้ง left_on และ right_on
– จังหวะที่ 3 **how=**: เลือกสไตล์ join — inner (เอาเฉพาะที่จับคู่ได้), left (เอาซ้ายทั้งหมด), right, outer (เอาทั้งหมด)
ที่เจ๋งคือ how=’left’ คือเวทมนตร์ที่ผมใช้บ่อยที่สุดในงานจริงครับ — รักษาทุกแถวของตารางซ้ายไว้เสมอ ถ้าตารางขวาไม่มีข้อมูลก็ได้ NaN กลับมา ไม่หายไปไหน เหมาะมากกับงานที่ข้อมูลอาจไม่ครบทุกฝั่ง ส่วนตัวผมใช้ merge เกือบทุกวันตอนทำ data pipeline ครับ 😎