Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C++

Regular cast vs static_cast vs dynamic_cast ใน C++

ประเภทของ Cast ใน C++

static_cast

ใช้สำหรับการแปลงชนิดข้อมูลปกติ (ordinary type conversion) ยังรวม implicit type coercion และเรียกได้โดยตรง ใช้ในกรณีเช่น:

  • แปลง float → int, char → int
  • แปลง pointer ระหว่างคลาสที่เกี่ยวข้อง (base ↔ derived) เมื่อแน่ใจว่าปลอดภัย (ไม่มี runtime check)
  • แปลง enum → int, void* → T*

dynamic_cast

ใช้สำหรับจัดการ polymorphism ใช้เฉพาะเมื่อ cast ไปยัง derived class (downcast) ต้องมี RTTI (Run-Time Type Information) และ base class ต้องมี virtual function อย่างน้อย 1 ตัว

  • Pointer: คืน nullptr หาก cast ไม่ได้ (ปลอดภัย)
  • Reference: โยน std::bad_cast exception หาก cast ไม่ได้
  • ใช้เมื่อ ไม่แน่ใจ ว่าออบเจ็กต์เป็นประเภท derived class จริงหรือไม่

Regular Cast (C-style cast)

รูปแบบ (Type)expr หรือ Type(expr) เป็น cast ที่ทรงพลังที่สุด เพราะรวม:

  • const_cast (เพิ่ม/ลบ const)
  • static_cast (การแปลงปกติ)
  • reinterpret_cast (reinterpret bit pattern)

แต่ unsafe เพราะไม่ใช้ dynamic_cast (ไม่มี runtime check) และอาจทำการแปลงที่อันตรายโดยไม่ได้ตั้งใจ (เช่น cast away const แล้ว modify → UB)

Cast อื่นๆ

const_cast

เพิ่มหรือลบ const/volatile qualifier เหมาะสำหรับ API เก่าที่ไม่ const-correct

reinterpret_cast

Reinterpret bit pattern ระดับต่ำสุด ใช้สำหรับ:

  • แปลง pointer ↔ integer
  • แปลง pointer type ที่ไม่เกี่ยวข้อง (T* → U*)
  • Type punning (อ่าน memory ด้วย type อื่น) - ต้องระมัดระวัง strict aliasing rules

แนวทางปฏิบัติที่ดี (Best Practices)

  1. หลีกเลี่ยง C-style cast ใช้ named casts แทน
  2. ใช้ static_cast สำหรับการแปลงที่แน่ใจว่าปลอดภัย (compile-time)
  3. ใช้ dynamic_cast สำหรับ downcasting ใน polymorphic hierarchy (runtime check)
  4. ใช้ const_cast เฉพาะเมื่อจำเป็นจริงๆ (API legacy)
  5. ใช้ reinterpret_cast น้อยที่สุด และ comment ให้ชัดเจนว่าทำไม
  6. C++20: ใช้ std::bit_cast สำหรับ type punning ที่ปลอดภัย