นากกายเสียบการ์ดฟิลด์ลงช่องสล็อตและแป้นคีย์เวิร์ดบนโต๊ะมิ้นต์

dataclass(slots=True, kw_only=True): ล็อกฟิลด์และบังคับคีย์เวิร์ด

น้องกายEngineering

เคยพิมพ์ชื่อฟิลด์ผิดแล้วอ็อบเจ็กต์เงียบๆ รับแอตทริบิวต์ใหม่ไหม ผมเคย จนเปิด slots=True

ตามเอกสาร dataclasses พารามิเตอร์ slots=True ทำให้คลาสใช้ __slots__ แทน __dict__ ทั่วไป จึงกันการสร้างแอตทริบิวต์นอกที่ประกาศ ส่วน kw_only=True บังคับส่งค่าเป็นคีย์เวิร์ดตอนสร้างอินสแตนซ์

เลือกเมื่อไหร่

  • slots=True: ต้องการกัน typo แอตทริบิวต์ และลดหน่วยความจำต่ออ็อบเจ็กต์จำนวนมาก
  • kw_only=True: ฟิลด์หลายตัวชนิดคล้ายกัน กลัวสลับตำแหน่งตอนเรียก
  • ระวัง: คลาสที่มี slots=True ใช้กับมัลติเพิลอินเฮริแตนซ์บางแบบต้องอ่านข้อจำกัดในเอกสารก่อน
from dataclasses import dataclass

@dataclass(slots=True, kw_only=True)
class Point:
    x: float
    y: float
    label: str = "origin"

p = Point(x=1.5, y=2.0, label="A")
assert p.x == 1.5 and p.label == "A"
try:
    Point(1.5, 2.0)
    raise AssertionError("positional should fail with kw_only")
except TypeError:
    pass
try:
    p.z = 3
    raise AssertionError("slots should block new attrs")
except AttributeError:
    pass
print("ok")

Recap

  1. เปิด slots=True เมื่ออยากกันแอตทริบิวต์เผลอๆ และประหยัดหน่วยความจำ
  2. เปิด kw_only=True เมื่อลำดับอาร์กิวเมนต์ทำให้สับสนง่าย
  3. อ่านข้อจำกัด inheritance ในเอกสารก่อนใช้ร่วมกับคลาสเก่า
  4. เขียนเทสต์สั้นๆ ว่าการสร้างแบบตำแหน่งและแอตทริบิวต์แปลกยังถูกปฏิเสธ