Best Practices ของผม – JavaScript
1. ปิดแคช
Firefox:
เปิด Developer Tools -> เปิด Settings (F1) -> "Disable HTTP Cache (when toolbox is open)"
Chrome:
เปิด Developer Tools -> เปิด Settings (F1) -> "Disable cache (while DevTools is open)"
2. เปิดคอนโซล JS ค้างไว้
ใน DevTools ให้เปิดแท็บ Console และเปิดค้างไว้ เพื่อให้ขั้นตอนที่ 1 ยังมีผลอยู่ และยังเห็นข้อผิดพลาดทั้งในเครือข่ายและใน JS ด้วย
ขอแนะนำปลั๊กอินตัวนี้ด้วย ซึ่งแสดงข้อผิดพลาดของ JS ได้ชัดเจนยิ่งขึ้น เผื่อเวลาที่คุณเองลืมคอยดู:
3. JavaScript: หนังสือที่ต้องอ่าน “You Don't Know JS”
- You Don't Know JS (1st Edition)
- อธิบายว่าทำไมควรหลีกเลี่ยง
this - อธิบายว่าทำไมบางครั้งใน JS จึงเกิดเรื่องที่ดูแปลก ๆ (คำสำคัญ: lexical scope, closure)
4. เครื่องหมายเซมิโคลอน
- ใส่ทุกครั้ง
- ไม่ได้บังคับ แต่ช่วยให้หลบหลุมพรางแบบนี้ได้ เป็นต้น: Stack Overflow
- JavaScript จะใส่เซมิโคลอนให้อัตโนมัติ:
// you want to return 5 and have ugly formatting:
return
5
// JavaScript Interpretation:
return;
5;
5. ตัวดำเนินการทางตรรกะ && และ ||
- ใน Java
a && bและa || bจะถูกประเมินตามพีชคณิตบูลีนaและbต้องเป็น boolean - ใน JavaScript:
- สำหรับ
a && bจะคืนค่าbเมื่อaเป็น true - สำหรับ
a || bจะคืนค่าbเมื่อaเป็น false
- สำหรับ
นิพจน์ก็เชื่อมแบบนี้ได้เช่นกัน ทำให้เขียน if-statement ที่สั้นที่สุดเท่าที่จะเป็นไปได้ – syntax sugar:
isAdmin && showDeleteButton();- (ถ้าพูดให้ถูกจริง ๆ นี่ไม่ใช่ statement แล้ว)
วิธีนี้ยังนิยมใช้กำหนดค่าเริ่มต้น (default value) ด้วย:
let sendNewsletter = form.getNewsletterOptIn() || false;
6. JavaScript ส่งค่าแบบ pass-by-reference หรือ pass-by-value?
เรื่องนี้ใน JavaScript น่าสนใจทีเดียว ตัวอย่าง:
function changeStuff(a, b, c) {
a = a * 10;
b.item = "changed";
c = {item: "changed"};
}
var num = 10;
var obj1 = {item: "unchanged"};
var obj2 = {item: "unchanged"};
changeStuff(num, obj1, obj2);
console.log(num);
console.log(obj1.item);
console.log(obj2.item);
ได้ผลลัพธ์ดังนี้:
10
changed
unchanged
ถ้า obj1 ไม่ใช่การอ้างอิง (reference) เลย การเปลี่ยน obj1.item ก็จะไม่มีผลใด ๆ กับ obj1 ที่อยู่นอกฟังก์ชัน
ถ้าอาร์กิวเมนต์เป็นการอ้างอิงจริง ๆ ทุกอย่างก็จะเปลี่ยนไป: num จะเป็น 100 และ obj2.item จะมีค่า “changed” แต่ในความเป็นจริง num ยังคงเป็น 10 และ
obj2.item ยังคงเป็น “unchanged”
ที่จริงแล้ว สิ่งที่ส่งเข้าไปถูกส่งแบบ by value แต่สิ่งที่ถูกส่งแบบ by value นั้นเองเป็นการอ้างอิง ในทางเทคนิคเรียกวิธีนี้ว่า call-by-sharing
ในทางปฏิบัติหมายความว่า ถ้าคุณเปลี่ยนตัวพารามิเตอร์เอง (เหมือน num และ obj2) จะไม่มีผลกับอ็อบเจกต์ต้นฉบับที่ส่งเข้ามาในฟังก์ชัน
แต่ถ้าเปลี่ยนค่าภายในของพารามิเตอร์ การเปลี่ยนแปลงนั้นจะมีผลออกไปด้วย (เหมือน obj1)