---
title: pandas set_index — ตั้งคอลัมน์เป็น index ของตาราง
url: https://www.thepexcel.com/functions/python/transform/pandas-set-index/
type: function-explainer
program: Python
syntax: "df.set_index(keys, drop, append)"
date: 2026-05-31
scores:
  popularity: 5
  difficulty: 3
  usefulness: 5
---

# pandas set_index — ตั้งคอลัมน์เป็น index ของตาราง

> set_index ใน pandas ผมใช้สำหรับตั้งคอลัมน์ใดคอลัมน์หนึ่ง (หรือหลายคอลัมน์) ให้กลายเป็น index หลักของ

## คำอธิบาย

set_index ใน pandas ผมใช้สำหรับตั้งคอลัมน์ใดคอลัมน์หนึ่ง (หรือหลายคอลัมน์) ให้กลายเป็น index หลักของ DataFrame เหมือนกับการกำหนดคีย์หลักให้ตาราง เพื่อให้ค้นหาข้อมูลด้วย .loc[] ได้อย่างรวดเร็วและตรงจุดครับ

## Syntax

```excel
df.set_index(keys, drop, append)
```

## Arguments

| Name | Required | Type | Default | Description |
| --- | --- | --- | --- | --- |
| keys | Yes | str \| list |  | ชื่อคอลัมน์ที่ต้องการตั้งเป็น index เช่น 'product_id' หรือ ['year', 'month'] สำหรับ MultiIndex |
| drop | No | bool | True | ถ้า True จะลบคอลัมน์ที่กลายเป็น index ออกจากส่วนข้อมูลปกติ (default) ถ้า False จะเก็บคอลัมน์นั้นไว้ด้วย |
| append | No | bool | False | ถ้า True จะเพิ่มคอลัมน์ที่เลือกต่อท้าย index เดิมแทนที่จะแทนที่ ใช้ตอนอยากเก็บ index เก่าไว้ด้วย |

## ตัวอย่าง

### 1. ตัวอย่างที่ 1: ตั้งคอลัมน์รหัสสินค้าเป็น index แล้วค้นหาด้วย .loc[]

```excel
df.set_index('product_id').loc['A002']
```

**ผลลัพธ์:** `name     ดินสอ
price       10
Name: A002, dtype: object`

ผมตั้ง product_id เป็น index ก่อน แล้วใช้ .loc['A002'] ดึงแถวของสินค้า A002 ออกมาได้เลยครับ สะอาดกว่าเขียน df[df['product_id'] == 'A002'] แบบเดิมมากเลย เหมือน VLOOKUP ใน Excel แต่อ่านง่ายกว่าเยอะ

### 2. ตัวอย่างที่ 2: ตั้ง MultiIndex จากสองคอลัมน์ แล้ว .loc[] ตามลำดับชั้น

```excel
df_mi.loc[2023]
```

**ผลลัพธ์:** `       sales
month       
Jan      100
Feb      150`

ผมตั้ง index สองชั้นจากคอลัมน์ year และ month พอจะดูข้อมูลปี 2023 ทั้งหมด ใช้ df_mi.loc[2023] ได้เลยครับ มันจะคืนทุกแถวที่ year เป็น 2023 มาให้ เหมือนการ drill-down ใน PivotTable ของ Excel ที่กด expand เพื่อดูรายปีเลย

### 3. ตัวอย่างที่ 3: ใช้ drop=False เพื่อเก็บคอลัมน์ index ไว้ในข้อมูลด้วย

```excel
df.set_index('product_id', drop=False)
```

**ผลลัพธ์:** `           product_id   name  price
product_id                         
A001             A001  ปากกา     25
A002             A002  ดินสอ     10
A003             A003  ยางลบ      5`

ปกติ set_index จะลบคอลัมน์ที่กลายเป็น index ออกจากส่วนข้อมูลครับ แต่ถ้าผมใส่ drop=False คอลัมน์ product_id ก็จะยังคงอยู่ในตารางด้วย ใช้ตอนที่ผมต้องการให้ product_id เป็นทั้ง index และยังเป็น column อยู่ในข้อมูลด้วยครับ เช่น ตอนจะ export หรือ merge ต่อ

### 4. ตัวอย่างที่ 4: .loc[] เจาะจง row+column หลัง set_index

```excel
df_idx.loc['A001', 'price']
```

**ผลลัพธ์:** `25`

อันนี้คือพลังเต็มๆ ของ set_index ครับ พอตั้ง product_id เป็น index แล้ว ผมใช้ .loc['A001', 'price'] ดึงราคาของสินค้า A001 ออกมาได้เป็น scalar เลย แบบเดียวกับที่ใน Excel เราใช้ INDEX-MATCH เพื่อหาค่าเฉพาะจุด แต่เขียนสั้นกว่ามากครับ

## หมายเหตุเพิ่มเติม

- 💡 ผมมักจะ set_index ก่อนเสมอตอนที่ต้องการ lookup หลายรอบครับ เพราะ .loc[] หลัง set_index เร็วและอ่านง่ายกว่าการ filter แบบ boolean ทุกครั้ง แต่ถ้า lookup แค่รอบเดียวก็ไม่จำเป็นต้อง set_index ครับ

- ถ้าใช้ MultiIndex แล้วอยากดูข้อมูลในระดับที่ 2 ให้ใช้ .loc[2023, 'Jan'] แบบ tuple ได้เลยครับ เช่น df_mi.loc[(2023, 'Jan')] จะได้แถวนั้นโดยตรงเลย ไม่ต้องกรองสองขั้น

## คำถามที่พบบ่อย

**Q: set_index แล้วข้อมูลเดิมเปลี่ยนไปด้วยไหม?**

ไม่ครับ pandas ไม่แก้ DataFrame เดิมของเรา แต่คืน DataFrame ใหม่ที่มี index ใหม่มาให้ ผมเลยต้องเขียน df_new = df.set_index('product_id') หรือถ้าอยากให้แก้ตัวเองเลยก็เพิ่ม inplace=True เข้าไปครับ แต่ผมไม่ค่อยแนะนำ inplace เพราะ debug ยากกว่า

**Q: ถ้า index มีค่าซ้ำกัน .loc[] จะได้ผลลัพธ์ยังไง?**

ถ้า index มีค่าซ้ำ .loc[] จะคืนแถวทั้งหมดที่ตรงกันออกมาเป็น DataFrame ครับ ไม่ใช่แถวเดียว เช่น ถ้าสินค้า A001 มีอยู่ 3 แถว df.loc['A001'] จะได้ DataFrame 3 แถว ผมเจอบ้างนะครับ ตอนแรกงงว่าทำไมได้หลายแถว สรุปคือ set_index ไม่บังคับว่า index ต้องไม่ซ้ำครับ ต่างจาก primary key ใน database

**Q: ต่างจาก df[df['col'] == value] ยังไง?**

ได้ผลเหมือนกันครับ แต่วิธีคิดและประสิทธิภาพต่างกัน df[df['col'] == value] คือการสแกนทุกแถวเพื่อเปรียบเทียบ ส่วน .loc[] หลัง set_index ใช้ index lookup ซึ่งเร็วกว่ามากเวลาข้อมูลเยอะครับ แถมโค้ดอ่านง่ายกว่าด้วย ผมเลยชอบ set_index + loc กว่าในกรณีที่ต้องค้นหาบ่อยๆ

## แหล่งข้อมูลเพิ่มเติม

- [pandas DataFrame.set_index (official docs)](https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.set_index.html) _(article)_

---

_Source: [https://www.thepexcel.com/functions/python/transform/pandas-set-index/](https://www.thepexcel.com/functions/python/transform/pandas-set-index/)_
