Programming Track
JavaScript
Type Coercion
Loose equality
เรียนรู้ว่า == แปลงชนิดก่อนเปรียบเทียบอย่างไร และทำไมการใช้ === เป็นค่าเริ่มต้นจึงปลอดภัยกว่า
`==` แปลงชนิดก่อนเปรียบเทียบ
`Loose equality` คือการเปรียบเทียบด้วย `==` ซึ่ง JavaScript อาจแปลงชนิดข้อมูลก่อนตัดสินว่าเท่ากันหรือไม่ ส่วน `===` เรียกว่า strict equality เพราะตรวจทั้งค่าและชนิดข้อมูล
`==` กับ `===` ให้ผลต่างกันJS
console.log("5" == 5); // true
console.log(0 == false); // true
console.log("" == false); // true
console.log("5" === 5); // false
console.log(0 === false); // false
console.log("" === false); // falseแนวทางเริ่มต้นที่ปลอดภัยคือใช้ `===` และ `!==` เพื่อไม่ให้ JavaScript แปลงชนิดให้ก่อนเทียบ
กฎการแปลงของ `==` โดยย่อ
- string กับ number — string ถูกแปลงเป็น number ก่อนเทียบ
- boolean กับประเภทอื่น — boolean ถูกแปลงเป็น number ก่อน (`true`→1, `false`→0)
- null กับ undefined — `==` มองว่าเท่ากัน (ใช้ `===` ถ้าไม่ต้องการ)
- object กับ primitive — object ถูกแปลงเป็น primitive ก่อนเทียบ
กฎพวกนี้ดูซับซ้อน จึงเป็นเหตุผลหลักที่แนะนำให้ใช้ `===` เป็นค่าเริ่มต้น
ข้อควรระวัง
- `null == undefined` เป็น `true` ผ่าน `==` แต่ `null === undefined` เป็น `false`
- `0 == ""` เป็น `true` เพราะ `""` แปลงเป็น `0` — เป็นคู่ที่ทำให้เกิด bug บ่อย
- `"\t\n" == 0` เป็น `true` เพราะ string ที่มีแต่ whitespace แปลงเป็น `0`
- `[] == false` เป็น `true` และ `[] == ![]` ก็เป็น `true` — แสดงให้เห็นความซับซ้อนของ `==`
- `NaN == NaN` เป็น `false` — NaN ไม่เท่ากับอะไรเลยรวมถึงตัวมันเอง แม้แต่กับ `==`
- แนวทางที่ดีคือใช้ `===` เสมอ และใช้ `==` เฉพาะเมื่อต้องการเปรียบเทียบ `null` กับ `undefined` พร้อมกัน