Lesson 03 · คาบเช้า 28 ต.ค. · ~25 นาที

K-means clustering และ Silhouette score

โยงกับสไลด์ ไม่มีสไลด์ (โค้ด 8 K-means + บันทึกคำพูด)

เป้าหมายบทนี้: อธิบายขั้นตอน K-means, ทำไมต้องสเกลข้อมูล, และอ่าน silhouette เพื่อเลือก k อย่างมีเหตุผล

1อัลกอริทึม

Centroid คือ "ตัวแทนกลุ่ม" รอบแรกเราสุ่มมามั่ว ๆ จึงยังไม่อยู่กลางกลุ่ม แล้วทำสองขั้นสลับกัน คือ อัปเดตสมาชิก และ อัปเดต centroid (ช่วงเช้า ไม่มีไทม์สแตมป์)

  1. ผู้ใช้กำหนด k (จำนวนกลุ่ม)
  2. สุ่ม centroid k จุด
  3. จัดสมาชิกแต่ละจุดเข้ากลุ่มของ centroid ที่ ใกล้ที่สุด (วัดด้วยระยะทาง จึงเรียกว่า distance-based)
  4. อัปเดต centroid ให้เป็น ค่าเฉลี่ย ของสมาชิกในกลุ่ม (เฉลี่ย x, เฉลี่ย y ... ตัวแทนอยู่กลางกลุ่ม)
  5. กลับไปข้อ 3 ทำซ้ำ

ลองกดทีละขั้น

กด ขั้นถัดไป สลับกัน: ขั้นคี่จัดสมาชิก (จุดเปลี่ยนสี) ขั้นคู่ย้าย centroid (กากบาทขยับไปกลางกลุ่ม เส้นประคือทางที่ขยับ) ลอง สุ่ม centroid ใหม่ ดูว่าจุดเริ่มต้นต่างกันใช้กี่รอบ

ถ้า centroid เริ่มต้นสุ่มได้ไม่ดี K-means อาจ converge ไปที่การแบ่งกลุ่มที่ไม่สวย (กดสุ่มใหม่หลายครั้งจะเห็น) นี่คือเหตุผลที่ผลขึ้นกับจุดเริ่มต้น

ลองเปลี่ยน k ใน config เป็น 4 หรือ 5 กับข้อมูลชุดเดิม (มีกลุ่มจริง 3 กลุ่ม) จะเห็นว่าแบ่งเกินก็ยัง "ทำงาน" แต่กลุ่มอธิบายยากขึ้น

หยุดเมื่อ converge (สมาชิกไม่เปลี่ยนกลุ่มอีก) หรือครบจำนวนรอบที่กำหนด (max iter) ชื่อ "K-means" มาจากการใช้ค่าเฉลี่ยเป็นตัวแทนกลุ่ม

ตัวอย่าง

อัปเดต centroid

กลุ่มสีแดงมีสมาชิก (อายุ, รายได้ในหน่วยพัน) = (20, 50), (30, 70), (25, 60) centroid ใหม่ = ( (20+30+25)/3 , (50+70+60)/3 ) = (25, 60)

หลัง centroid ขยับ สมาชิกบางจุดต้องเปลี่ยนกลุ่มไหม

อาจต้อง เพราะจุดนั้นอาจใกล้ centroid ของกลุ่มอื่นมากกว่าแล้ว จึงต้องทำซ้ำ (เมื่อสมาชิกไม่เปลี่ยนจึงหยุด)

2ก่อนทำ K-means ต้องเตรียมข้อมูล

ใช้ระยะทางจึงต้อง:

ตัวอย่าง

ทำไมต้องสเกล

คน A อายุ 30 รายได้ 50,000 กับคน B อายุ 40 รายได้ 50,000 → ระยะ = \( \sqrt{10^2+0^2}=10 \) คน A กับคน C อายุ 30 รายได้ 50,020 → ระยะ = \( \sqrt{0^2+20^2}=20 \) อายุต่างกัน 10 ปี (ต่างมาก) กลับ "ใกล้" กว่ารายได้ที่ต่างกันแค่ 20 บาท

อาจารย์ย้ำว่า ถ้าสั่ง GenAI สร้างโมเดลให้ มันอาจไม่เตรียมข้อมูลให้ถูก (ไม่สเกล) ผลจึงผิดได้ ต้องตรวจเอง

3ใช้ใน sklearn

from sklearn.cluster import KMeans
km = KMeans(n_clusters=4)        # default n_clusters=8, max_iter=300
km.fit(X_scaled)                 # ใส่เฉพาะตัวแปรต้น ไม่ใส่ y
km.cluster_centers_              # centroid (ยังอยู่ในสเปซที่สเกลแล้ว)
km.labels_                       # กลุ่มของสมาชิกแต่ละตัว
km.predict(X_new)                # ลูกค้าใหม่อยู่กลุ่มไหน

fit ใส่แต่ตัวแปรต้น ไม่ใส่ตัวแปรตาม เพราะเป็น unsupervised พอ fit เสร็จจะมี centroid และมีกลุ่มของสมาชิกแต่ละตัว แล้ว predict ข้อมูลใหม่ได้ว่าอยู่กลุ่มไหน (ช่วงเช้า ไม่มีไทม์สแตมป์)

ถ้า centroid อยู่ในสเปซที่สเกลแล้ว (ค่าติดลบ/บวกแปลก ๆ) ต้อง inverse_transform กลับสเปซเดิมก่อนถึงอ่านรู้เรื่อง เช่น กลุ่มที่อายุ −1.2 ไม่ได้แปลว่าอายุติดลบ

4ผลลัพธ์ที่ต้องอธิบายให้ได้

อาจารย์เล่นตัวอย่างโรงแรม: สามกลุ่มจากอายุ+รายได้ ถ้าจะเสนอ กระโดดร่มราคา 2 หมื่น ต้องเสนอกลุ่ม อายุน้อย รายได้สูง ส่วนกลุ่มอายุมากไม่เหมาะ (อาจารย์ล้อเล่นเรื่องตายก่อน) แต่หลักคือ

ผลลัพธ์ของ unsupervised คือ insight เราต้อง อธิบายแต่ละกลุ่มได้ แล้วเอาไปใช้ ถ้าอธิบายไม่ได้ก็ไม่มีประโยชน์

5เลือก k: Silhouette score

ไม่มีกฎตายตัวว่า k ควรเป็นเท่าไร (ถ้าเป็นนักเรียนในห้อง จะแบ่ง 3 หรือ 5 กลุ่มก็แล้วแต่ว่าดูแลได้เหมาะไหม) มีตัวช่วยวัด "คุณภาพกลุ่ม" คือ silhouette

$$ s_i = \frac{b_i - a_i}{\max(a_i, b_i)} $$

ตัวอย่าง

คำนวณ silhouette

จุดหนึ่งมี a = 1 และ b = 8.5 → \( s=(8.5-1)/8.5\approx 0.88 \) (เกาะกลุ่มดี แยกจากกลุ่มอื่นชัด) ถ้า a = 6 และ b = 2 → \( s=(2-6)/6\approx -0.67 \) (น่าจะอยู่ผิดกลุ่ม)

ลองเลื่อน k เอง

เลื่อน \( k \) จาก 2 ถึง 6 บนข้อมูลชุดเดียวกัน ดูภาพกลุ่มพร้อมคะแนน silhouette ของแต่ละ k

อย่าเลือก k จาก silhouette สูงสุดอย่างเดียว

อาจารย์ทดลอง k = 2, 3, 4, 5, 6 พบว่า k = 2 ได้ silhouette สูงสุด แต่ถ้าพล็อตจะเห็นว่า หยาบเกินใช้ประโยชน์ไม่ได้ อาจารย์จึงเลือก k = 4 ซึ่ง silhouette ต่ำกว่านิดหน่อยแต่ใช้งานได้

ประโยคนี้ผิด: "ต้องจัด 2 กลุ่มเท่านั้นเพราะ silhouette สูงสุด" Silhouette เป็นแค่ guideline ว่าควรลอง k ช่วงไหน แล้วเลือกที่ใช้ประโยชน์ได้ อาจารย์บอกว่านี่อาจออกสอบทฤษฎี (ช่วงเช้า ไม่มีไทม์สแตมป์)

6การใช้ clustering ช่วยโมเดลทำนาย

โมเดลเดียวทำนายราคาที่ดินทั้งประเทศอาจไม่แม่น เพราะกรุงเทพมีรถไฟฟ้าแต่เชียงใหม่ไม่มี แต่ถ้า แบ่งกลุ่มก่อน (หรือแบ่งตามจังหวัด) แล้วทำโมเดลแยกกลุ่ม จะแม่นขึ้น

7ลองทำ

อ่านเพิ่ม / ที่มา

ติดตรงไหน ถาม Claude ได้เลย บอกเลขบทกับเลขข้อมาด้วย