กฎต่างๆ ของวิศวกรรมซอฟต์แวร์
(lawsofsoftwareengineering.com)- คอลเล็กชันที่รวบรวม หลักการและแพตเทิร์น 56 ข้อ ที่ส่งผลต่อระบบซอฟต์แวร์ ทีม และการตัดสินใจไว้ในที่เดียว ครอบคลุมตั้งแต่การบริหารทีมไปจนถึงสถาปัตยกรรม คุณภาพ การออกแบบ และการตัดสินใจ
- กฎที่เกี่ยวกับทีม เช่น กฎของ Conway, กฎของ Brooks และตัวเลขของ Dunbar แสดงให้เห็นว่าโครงสร้างองค์กรส่งผลโดยตรงต่อการออกแบบระบบและประสิทธิภาพการทำงาน
- ในด้านสถาปัตยกรรม มีการสรุปข้อจำกัดและหลักการที่ต้องคำนึงถึงเมื่อออกแบบระบบที่ซับซ้อน เช่น กฎของ Hyrum, ทฤษฎีบท CAP และกฎของ Gall
- กฎที่เกี่ยวกับคุณภาพกล่าวถึง หนี้ทางเทคนิค, พีระมิดการทดสอบ และกฎของ Kernighan ซึ่งสะท้อนความยากในโลกจริงของการรักษาคุณภาพโค้ดและการดีบัก
- ในด้านการตัดสินใจ ครอบคลุมอคติทางความคิดและเกณฑ์การตัดสินที่มักเกิดขึ้นระหว่างการพัฒนา เช่น ผล Dunning-Kruger, ความผิดพลาดจากต้นทุนจม และหลักการพาเรโต
ทีม (Teams)
1. กฎของ Conway (Conway's Law)
> องค์กรจะออกแบบระบบที่สะท้อนโครงสร้างการสื่อสารของตนเอง
- สถาปัตยกรรมซอฟต์แวร์มักมีแนวโน้มที่จะเป็นไปตาม โครงสร้างการสื่อสารขององค์กร ที่สร้างมันขึ้นมาโดยธรรมชาติ
- หากทีมถูกแบ่งออกเป็น 3 ทีม ระบบก็มักมีแนวโน้มถูกแบ่งออกเป็น 3 โมดูลใหญ่เช่นกัน
- ยังมี "กลยุทธ์ Conway แบบย้อนกลับ" (Inverse Conway Maneuver) ที่ใช้แนวคิดนี้ในทางกลับกัน คือปรับโครงสร้างทีมให้เข้ากับสถาปัตยกรรมที่ต้องการก่อน
- เมื่อนำ microservices มาใช้ การทำให้ขอบเขตของทีมสอดคล้องกับขอบเขตของบริการจะมีประสิทธิภาพ
2. กฎของ Brooks (Brooks's Law)
> การเพิ่มคนเข้าไปในโครงการซอฟต์แวร์ที่ล่าช้า จะยิ่งทำให้ช้าลงกว่าเดิม
- เมื่อมีคนใหม่เข้าร่วม สมาชิกทีมเดิมจะต้อง ใช้เวลาไปกับการสอนและประสานงาน ทำให้ประสิทธิภาพรวมลดลงชั่วคราว
- เมื่อจำนวนสมาชิกทีมเพิ่มขึ้น เส้นทางการสื่อสารจะเพิ่มขึ้นแบบทวีคูณ (เมื่อมี n คน จะมี n(n-1)/2 เส้นทาง)
- Frederick Brooks วางหลักการนี้ไว้ในหนังสือ The Mythical Man-Month เมื่อปี 1975 โดยอิงจากประสบการณ์ในโครงการ IBM OS/360
- สามารถอธิบายเชิงปริมาณได้ด้วย กฎของ Little (L = λ × W): เมื่อเพิ่มคน WIP (งานที่กำลังทำอยู่) จะเพิ่มขึ้น แต่ throughput กลับทรงตัว ทำให้ lead time เพิ่มขึ้นแทน
- ทางออกไม่ใช่การเพิ่มคน แต่เป็นการ ปรับขอบเขตงานหรือเปลี่ยนกำหนดการ
3. ตัวเลขของ Dunbar (Dunbar's Number)
> ขีดจำกัดทางการรับรู้ของความสัมพันธ์ที่คนหนึ่งสามารถรักษาได้อย่างมั่นคงอยู่ที่ราว 150 คน
- Robin Dunbar ได้ตัวเลขนี้จากความสัมพันธ์ระหว่างขนาดสมองของไพรเมตกับขนาดของกลุ่มสังคม
- ลำดับชั้นทางสังคม ของ Dunbar: ~5 คน (ความสัมพันธ์ใกล้ชิด), ~15 คน (ผู้ร่วมงานที่ไว้วางใจได้), ~50 คน (ความสัมพันธ์ในการทำงานที่ใกล้ชิด), ~150 คน (ความเชื่อมโยงทางสังคมที่มั่นคง)
- เมื่อองค์กรวิศวกรรมมีขนาดเกิน 150 คน การสื่อสารแบบไม่เป็นทางการจะเริ่มถึงขีดจำกัด จึงจำเป็นต้องมี ลำดับชั้นและกระบวนการที่เป็นทางการ
- "Two-Pizza Team" ของ Amazon (5~10 คน) ก็สะท้อนว่าต่อให้อยู่ในองค์กรที่มีไม่เกิน 150 คน การทำงานร่วมกันจริงก็มักเกิดขึ้นในหน่วยย่อยที่เล็กกว่านั้น
4. ผล Ringelmann (The Ringelmann Effect)
> ยิ่งขนาดของกลุ่มใหญ่ขึ้น ผลิตภาพของแต่ละคนยิ่งลดลง
- เป็นปรากฏการณ์ "การอู้งานทางสังคม" (social loafing) ที่ยิ่งสมาชิกในกลุ่มมีมาก การมีส่วนร่วมของแต่ละคนยิ่งลดลง
- ในทีมซอฟต์แวร์เช่นกัน เมื่อทีมมีขนาดใหญ่ขึ้น ความรับผิดชอบรายบุคคลจะถูกเจือจางและต้นทุนในการประสานงานจะเพิ่มขึ้น
- อธิบายได้ว่าทำไมทีมขนาดเล็กจึงสร้างผลงานต่อคนได้สูงกว่า
5. กฎของ Price (Price's Law)
> จำนวนคนที่เท่ากับรากที่สองของจำนวนผู้เข้าร่วมทั้งหมด จะทำงานคิดเป็น 50% ของงานทั้งหมด
- ในองค์กรที่มี 100 คน จะมีประมาณ 10 คนที่รับผิดชอบงานครึ่งหนึ่งของทั้งหมด
- ยิ่งองค์กรใหญ่ขึ้น การพึ่งพาคนผลงานสูงเพียงไม่กี่คนก็ยิ่งรุนแรงขึ้น
- อธิบายได้ว่าทำไมเมื่อขยายทีม ผลิตภาพจึงไม่ได้เพิ่มขึ้นแบบเส้นตรง
6. กฎของ Putt (Putt's Law)
> คนที่เข้าใจเทคโนโลยีจะไม่ได้บริหาร และคนที่บริหารจะไม่เข้าใจเทคโนโลยี
- เป็นการเสียดสี ช่องว่างระหว่างบทบาทการจัดการกับความเชี่ยวชาญทางเทคนิค ในองค์กรเทคนิค
- เมื่อต้องออกแบบโครงสร้างผู้นำด้านเทคนิค จำเป็นต้องตระหนักถึงช่องว่างนี้และเตรียมกลไกมาชดเชย
7. หลักการ Peter (Peter Principle)
> ในองค์กร พนักงานทุกคนมีแนวโน้มจะได้รับการเลื่อนตำแหน่งไปจนถึงระดับที่ตนเองไร้ความสามารถ
- คนที่มีความสามารถในบทบาทหนึ่ง เมื่อได้เลื่อนตำแหน่ง อาจเกิดรูปแบบที่ กลายเป็นคนไร้ความสามารถในบทบาทใหม่
- สะท้อนความจริงที่ว่านักพัฒนาที่ยอดเยี่ยมไม่ได้แปลว่าจะเป็นผู้จัดการที่ดีเสมอไป
- จึงจำเป็นต้องมีระบบ dual ladder ที่แยกเส้นทาง IC (Individual Contributor) ออกจากเส้นทางบริหาร
8. Bus Factor
> จำนวนขั้นต่ำของสมาชิกทีมที่หากหายไปจะทำให้โครงการตกอยู่ในความเสี่ยงร้ายแรง
- หาก Bus Factor เท่ากับ 1 แปลว่ามี จุดล้มเหลวเพียงจุดเดียว (Single Point of Failure)
- การแบ่งปันความรู้, pair programming และการจัดทำเอกสารเป็นสิ่งสำคัญในการเพิ่ม Bus Factor
- การทำ code review และ cross-training เป็นวิธีที่ใช้ได้จริงในการปรับปรุง Bus Factor
9. หลักการ Dilbert (Dilbert Principle)
> บริษัทมีแนวโน้มจะเลื่อนพนักงานที่ไร้ความสามารถไปเป็นผู้จัดการเพื่อจำกัดความเสียหาย
- เป็นข้อสังเกตเชิงเสียดสีที่เสนอโดย Scott Adams และถือเป็นรูปแบบหนึ่งของหลักการ Peter
- เป็น ปรากฏการณ์เชิงย้อนแย้งในองค์กร ที่มองว่าตำแหน่งบริหารคือที่ที่สร้างความเสียหายต่องานจริงได้น้อยที่สุด
การวางแผน (Planning)
10. การปรับแต่งเร็วเกินไป / หลักการเพิ่มประสิทธิภาพของ Knuth (Premature Optimization)
> การปรับแต่งเร็วเกินไปคือรากเหง้าของความชั่วร้ายทั้งมวล
- Donald Knuth เสนอไว้ในบทความปี 1974 ว่า: "ในประมาณ 97% ของกรณี ประสิทธิภาพเล็กน้อยนั้นควรถูกมองข้าม"
- เนื่องจากโค้ดประมาณ 20% ใช้เวลาทำงานถึง 80% การไปปรับแต่งโค้ดอีก 80% ที่เหลือจึงเป็นความสูญเปล่า
- ลำดับที่ถูกต้องคือ ทำให้มันทำงานได้ก่อน → ทำให้มันถูกต้อง → แล้วค่อยทำให้มันเร็วหากจำเป็น
- โค้ดที่ถูกปรับแต่งแล้วมักซับซ้อนขึ้น จึงควรใช้ profiling เพื่อตรวจสอบ คอขวดที่แท้จริง ก่อนจึงค่อยลงมือ
11. กฎของ Parkinson (Parkinson's Law)
> งานจะขยายตัวจนเต็มเวลาที่ได้รับมา
- หากเดดไลน์คือ 2 สัปดาห์ งานก็จะยืดออกไป 2 สัปดาห์ ถ้าเป็น 4 สัปดาห์ งานก็จะยืดไป 4 สัปดาห์
- นี่คือเหตุผลที่การกำหนด milestone ที่สั้นและชัดเจน จึงสำคัญในโครงการซอฟต์แวร์
- Agile แบบอิง sprint เป็นวิธีรับมือกับกฎนี้ที่ใช้ได้จริง
12. กฎ 90-90 (The Ninety-Ninety Rule)
> โค้ด 90% แรกใช้เวลา 90% ของเวลาพัฒนา และอีก 10% ที่เหลือก็ใช้เวลาเพิ่มอีก 90%
- เตือนให้เห็นว่า 10% สุดท้ายของโครงการซอฟต์แวร์ (edge case, การเก็บรายละเอียด, การแก้บั๊ก) มักใช้เวลานานกว่าที่คาดมาก
- คำว่า "เกือบเสร็จแล้ว" ในความเป็นจริงอาจหมายถึงเพิ่งมาถึง ครึ่งทางของกำหนดการทั้งหมด
13. กฎของ Hofstadter (Hofstadter's Law)
> ไม่ว่าคุณจะเผื่อกฎของ Hofstadter ไว้แล้วก็ตาม มันก็ยังใช้เวลานานกว่าที่คาดเสมอ
- เป็นกฎที่มีโครงสร้างแบบ อ้างอิงตัวเองเชิงเวียนกลับ ซึ่งอธิบายความยากโดยธรรมชาติของการประเมินเวลางานซอฟต์แวร์
- แม้จะเพิ่ม buffer เข้าไปแล้ว ก็ยังมักเกินกำหนดอยู่ดี
- Douglas Hofstadter แนะนำกฎนี้ไว้ในหนังสือ Gödel, Escher, Bach เมื่อปี 1979
14. กฎของ Goodhart (Goodhart's Law)
> เมื่อดัชนีชี้วัดกลายเป็นเป้าหมาย มันจะไม่ใช่ดัชนีชี้วัดที่ดีอีกต่อไป
- ตัวอย่างที่ชัดเจนคือเมื่อกำหนด code coverage เป็น KPI ก็มักจะเกิดการสร้างเทสต์ที่ไม่มีความหมายจำนวนมาก
- หากวัดผลิตภาพด้วยจำนวนบรรทัดโค้ด (LOC) ก็จะได้ โค้ดที่ยืดยาวโดยไม่จำเป็น
- ควรมุ่งเน้นที่ การบรรลุคุณค่าที่แท้จริง มากกว่าการไล่ทำให้ตัวเลขสวย
15. กฎของ Gilb (Gilb's Law)
> สิ่งที่ต้องการการวัดผลนั้น การวัดไม่ว่าวิธีใดย่อมดีกว่าไม่วัดเลย
- แม้จะวัดได้ไม่สมบูรณ์ การวัดแบบคร่าว ๆ ก็ยังมีประโยชน์เสมอมากกว่าการไม่วัด
- ใช้ได้กับสิ่งที่วัดเชิงปริมาณได้ยาก เช่น คุณภาพซอฟต์แวร์ หรือความพึงพอใจของผู้ใช้
สถาปัตยกรรม (Architecture)
16. กฎของ Hyrum (Hyrum's Law)
> หากมีผู้ใช้ API มากพอ จะต้องมีใครสักคนพึ่งพาพฤติกรรมทุกอย่างของระบบที่สังเกตเห็นได้
- ไม่ได้มีเพียงสเปก API อย่างเป็นทางการเท่านั้นที่กลายเป็นสิ่งที่ถูกพึ่งพา แต่รวมถึงพฤติกรรมที่ไม่เป็นทางการอย่าง จังหวะเวลา รูปแบบข้อความ error และลำดับการจัดเรียง ด้วย
- กรณีของ Microsoft Windows ที่คงพฤติกรรมเวอร์ชันเก่าไว้เพื่อให้แอป third-party ที่พึ่งพา พฤติกรรมและบั๊กที่ไม่ได้มีการจัดทำเอกสาร ในอดีตยังคงใช้งานร่วมกันได้
- Google’s Hyrum Wright สังเกตสิ่งนี้จากประสบการณ์การเปลี่ยนแปลงไลบรารีภายใน Google ราวปี 2011-2012
- เพื่อนร่วมงาน Titus Winters ตั้งชื่อให้ว่า "Hyrum's Law" (อยู่ใน Software Engineering at Google)
- สัญญาที่แท้จริงในทางปฏิบัติไม่ใช่ API ทางการ แต่คือพฤติกรรมทั้งหมดที่สังเกตได้จริง
17. กฎของ Gall (Gall's Law)
> ระบบที่ซับซ้อนและใช้งานได้จริง ย่อมวิวัฒนาการมาจากระบบที่เรียบง่ายและใช้งานได้จริง
- หากออกแบบระบบที่ซับซ้อนตั้งแต่แรก จะมีตัวแปรที่ยังไม่ผ่านการพิสูจน์มากเกินไป ทำให้มีโอกาสล้มเหลวสูง
- เป็นพื้นฐานเชิงทฤษฎีของแนวทาง MVP(Minimum Viable Product)
- ตัวอย่างของ Facebook ที่เริ่มจากระบบโปรไฟล์อย่างง่ายสำหรับนักศึกษา Harvard ในปี 2004 แล้วค่อยๆ ขยายออกไป
- แม้แต่ตอนเปลี่ยนไปใช้ไมโครเซอร์วิส การ เริ่มจาก monolith แล้วค่อยๆ แยกออก ก็ได้เปรียบกว่า
- John Gall เสนอไว้ในหนังสือ Systemantics เมื่อปี 1975 (กลายเป็นหนังสือ cult classic หลังถูกสำนักพิมพ์ปฏิเสธ 30 แห่งก่อนตีพิมพ์)
18. กฎของการนามธรรมที่รั่วไหล (The Law of Leaky Abstractions)
> abstraction ที่ไม่เป็นเรื่องพื้นๆ (non-trivial) ทุกแบบ ล้วนมีการรั่วไหลในระดับหนึ่ง
- ORM ซ่อน SQL ไว้ แต่เมื่อเกิดปัญหาด้านประสิทธิภาพ ก็มักต้องกลับไปตรวจดู query ที่ถูกสร้างขึ้นจริง ซึ่งเป็นตัวอย่างที่ชัดเจน
- garbage collection ของ Java/Python ก็เป็น abstraction เช่นกัน แต่พฤติกรรมภายในอย่างการหยุดชั่วคราวของ GC ก็ส่งผลต่อประสิทธิภาพได้
- บทเรียนไม่ใช่ว่า abstraction เป็นสิ่งไม่ดี แต่คือควร เตรียมพร้อมเมื่อ abstraction พังลง
- Joel Spolsky แนะนำแนวคิดนี้ในบล็อกโพสต์ปี 2002 พร้อมตัวอย่างอย่าง TCP และ virtual memory
- ยังเชื่อมโยงเชิงบริบทกับคำกล่าวของ George Box ที่ว่า "โมเดลทั้งหมดล้วนผิด แต่บางโมเดลก็ยังมีประโยชน์"
19. กฎของ Tesler / กฎการอนุรักษ์ความซับซ้อน (Tesler's Law)
> ทุกแอปพลิเคชันมีความซับซ้อนเฉพาะตัวที่ไม่อาจลบออกได้ ทำได้เพียงย้ายที่ ไม่สามารถกำจัดทิ้งได้
- คำถามหลักคือ: ใครจะเป็นผู้รับภาระความซับซ้อน (ผู้ใช้ vs ระบบ)
- Calendly ดูดซับความซับซ้อนของการนัดหมายไว้ในระบบ ขณะที่อีเมลเธรดผลักภาระนั้นให้ผู้ใช้
- การออกแบบที่ดีคือการย้ายความซับซ้อนจาก ประสบการณ์ผู้ใช้ไปไว้ภายในระบบ
- Larry Tesler วางหลักการนี้ไว้ในช่วงทศวรรษ 1980 ระหว่างทำงานกับ Apple Lisa และ GUI ยุคแรก
20. CAP Theorem
> ระบบกระจายไม่สามารถรับประกันได้พร้อมกันทั้ง Consistency (C), Availability (A) และ Partition Tolerance (P) ครบทั้งสามอย่าง ทำได้เพียงสองอย่าง
- เนื่องจาก network partition เป็นสิ่งที่หลีกเลี่ยงไม่ได้ในโลกจริง ทางเลือกที่แท้จริงจึงเป็น consistency vs availability
- ระบบแบบ CP (เช่น MongoDB): เมื่อเกิด partition จะบล็อกการเขียนเพื่อรักษาการซิงก์ของ replica ทั้งหมด
- ระบบแบบ AP (เช่น Cassandra, DNS): ยังคงตอบสนองต่อ request ระหว่างเกิด partition ได้ โดยยอมให้เกิดความไม่สอดคล้องกันชั่วคราวระหว่าง replica
- Eric Brewer เสนอแนวคิดนี้ในบริบทของเว็บเซอร์วิสเมื่อปี 2000 และ Gilbert & Lynch พิสูจน์อย่างเป็นทางการในปี 2002
21. ปรากฏการณ์ Second-System (Second-System Effect)
> หลังจากระบบเล็กๆ ที่ประสบความสำเร็จ มักตามมาด้วยระบบรุ่นถัดไปที่ถูกออกแบบเกินพอดีและบวมเทอะทะ
- เป็นแพตเทิร์นที่เมื่อได้ความมั่นใจจากความสำเร็จของระบบแรก ก็จะ เททุกไอเดียลงไป ในระบบที่สอง
- สาเหตุหลักคือ feature creep และ over-generalization
- Frederick Brooks ระบุปรากฏการณ์นี้ไว้ใน The Mythical Man-Month
22. Fallacies of Distributed Computing
> 8 สมมติฐานที่ผิดพลาดซึ่งผู้คนที่ออกแบบระบบกระจายเป็นครั้งแรกมักมี
- ความเข้าใจผิดทั้ง 8 ข้อ: (1) เครือข่ายเชื่อถือได้, (2) latency เป็นศูนย์, (3) bandwidth ไม่มีที่สิ้นสุด, (4) เครือข่ายปลอดภัย, (5) topology ไม่เปลี่ยน, (6) มีผู้ดูแลเพียงคนเดียว, (7) ค่าใช้จ่ายในการส่งข้อมูลเป็นศูนย์, (8) เครือข่ายมีความเป็นเนื้อเดียวกัน
- หากออกแบบโดยตั้งอยู่บนสมมติฐานเหล่านี้ ก็จะเกิด ปัญหาขัดข้องและปัญหาด้านประสิทธิภาพที่ไม่คาดคิด ใน production
23. กฎของผลลัพธ์ที่ไม่ตั้งใจ (Law of Unintended Consequences)
> เมื่อเปลี่ยนแปลงระบบที่ซับซ้อน ต้องคาดไว้เสมอว่าจะมีผลลัพธ์ที่ไม่คาดคิดเกิดขึ้น
- เมื่อเปลี่ยนคอมโพเนนต์หนึ่งของระบบ ก็อาจเกิดผลข้างเคียงใน จุดที่คาดไม่ถึง
- เป็นหลักการที่สนับสนุนความจำเป็นของ chaos engineering และการทดสอบอย่างครอบคลุม
24. กฎของ Zawinski (Zawinski's Law)
> ทุกโปรแกรมพยายามขยายตัวไปเรื่อยๆ จนกว่าจะอ่านเมลได้
- เป็นการเสียดสีปรากฏการณ์ feature bloat ที่เมื่อซอฟต์แวร์ประสบความสำเร็จ ก็มักถูกเพิ่มฟีเจอร์มากขึ้นเรื่อยๆ
- Jamie Zawinski (นักพัฒนายุคแรกของ Netscape) เป็นผู้สังเกตปรากฏการณ์นี้
- เป็นคำเตือนถึงแนวโน้มที่เครื่องมือเรียบง่ายเมื่อเวลาผ่านไปจะพยายามกลายเป็นแพลตฟอร์มสารพัดประโยชน์
คุณภาพ (Quality)
25. กฎ Boy Scout (The Boy Scout Rule)
> ควรปล่อยโค้ดไว้ในสภาพที่ดีกว่าตอนที่เราเจอ
- แก่นสำคัญไม่ใช่การ refactor ครั้งใหญ่ แต่เป็น การปรับปรุงอย่างต่อเนื่องและค่อยเป็นค่อยไป
- ลงมือทำ การปรับปรุงเล็กๆ ทุกครั้ง เช่น เปลี่ยนชื่อฟังก์ชันที่ชวนสับสน ลบโค้ดซ้ำ เพิ่มเทสต์ที่ขาดหาย
- Robert C. Martin (Uncle Bob) นำมาใช้กับการพัฒนาซอฟต์แวร์ใน Clean Code (2008)
- หลักการของวิศวกร Google "If you touch it, you own it" — เมื่อแก้โค้ดแล้ว ก็ต้องรับผิดชอบต่อคุณภาพของส่วนนั้นด้วย
- การทำตามกฎนี้ช่วยป้องกัน ปรากฏการณ์หน้าต่างแตก (Broken Windows) และไม่ให้หนี้ทางเทคนิคสะสม
26. กฎของ Murphy (Murphy's Law)
> สิ่งใดที่ผิดพลาดได้ สิ่งนั้นย่อมผิดพลาด
- เป็นพื้นฐานของ defensive programming, การจัดการ exception และการออกแบบเพื่อรับมือความขัดข้อง
- ในซอฟต์แวร์ ต้องออกแบบ error handling และ fallback ด้วยท่าทีว่า "error ที่เกิดขึ้นได้ ย่อมเกิดขึ้นแน่"
27. กฎของ Postel / หลักความทนทาน (Postel's Law)
> จงเข้มงวดกับสิ่งที่ตัวเองทำ และผ่อนปรนกับสิ่งที่รับมาจากผู้อื่น
- ในการออกแบบ API หลักการคือ output ต้องปฏิบัติตามสเปกอย่างเคร่งครัด แต่ input ควรยืดหยุ่นพอที่จะรับรูปแบบที่หลากหลายได้
- Jon Postel วางหลักความทนทาน (Robustness Principle) นี้ระหว่างการออกแบบโปรโตคอล TCP/IP
- เป็นแนวทางเชิงปฏิบัติที่ช่วยเพิ่ม interoperability ระหว่างระบบ
28. ทฤษฎีหน้าต่างแตก (Broken Windows Theory)
> อย่าปล่อยทิ้งไว้ทั้งการออกแบบที่แย่ การตัดสินใจที่ผิด และโค้ดคุณภาพต่ำ
- หากปล่อย "หน้าต่างแตก" เพียงบานเดียว (โค้ดที่ไม่ดี) ไว้ ก็จะนำไปสู่ การเสื่อมคุณภาพเพิ่มเติม
- เมื่อใน codebase มีทั้งคอมเมนต์ TODO, dead code และคำเตือนที่ยังไม่ถูกแก้สะสมอยู่ โค้ดใหม่ก็มักถูกเขียนออกมาในมาตรฐานที่ต่ำลงด้วย
- วัฒนธรรมที่สำคัญคือแม้เป็นปัญหาเล็กน้อยก็ต้องแก้ทันทีที่พบ
29. หนี้ทางเทคนิค (Technical Debt)
> ทุกปัจจัยที่ทำให้ความเร็วในการพัฒนาซอฟต์แวร์ลดลง
- Ward Cunningham ใช้คำนี้ครั้งแรกเป็นอุปมาเชิงการเงินในงาน OOPSLA ปี 1992: หากเลือกทางลัดในการเขียนโค้ด ก็เท่ากับ ยืมเวลาจากอนาคต
- เงินต้น (ต้นทุนในการแก้) + ดอกเบี้ย (ประสิทธิภาพการทำงานที่ลดลงอย่างต่อเนื่องจากโค้ดที่รก)
- หนี้ทางเทคนิคแบบตั้งใจบางครั้งก็สมเหตุสมผล (จังหวะเวลาออกสู่ตลาด, การทำ prototype) แต่ แผนชำระหนี้ เป็นสิ่งจำเป็น
- ตัวอย่างคลาสสิกคือการข้าม automated test: อาจปล่อยรีลีสได้สำเร็จ แต่หลังจากนั้นทุกครั้งที่มีการเปลี่ยนแปลงก็จะเกิดบั๊กที่ไม่คาดคิด
- วิธีแก้: refactor, เพิ่มเทสต์ที่ขาด และปรับปรุงการออกแบบ
30. กฎของ Linus (Linus's Law)
> หากมีผู้ตรวจมากพอ บั๊กทุกตัวก็จะถูกพบได้ง่าย
- เป็นหลักการสำคัญของการพัฒนาโอเพนซอร์ส: เมื่อมี สายตาจำนวนมาก ช่วยกันตรวจโค้ด บั๊กก็กลายเป็นเรื่องเล็ก
- Eric Raymond ตั้งชื่อนี้ตาม Linus Torvalds ใน The Cathedral and the Bazaar
- สนับสนุนความสำคัญของวัฒนธรรม code review
31. กฎของ Kernighan (Kernighan's Law)
> การดีบักยากกว่าการเขียนโค้ดครั้งแรกเป็นสองเท่า
- ดังนั้น ถ้าเขียนโค้ดอย่างชาญฉลาดเกินไป ก็จะไม่ฉลาดพอเวลาต้องดีบัก
- นี่คือเหตุผลที่ควรเขียนโค้ดที่เรียบง่ายและอ่านง่าย
- Brian Kernighan นำเสนอไว้ใน The Elements of Programming Style
32. พีระมิดการทดสอบ (Testing Pyramid)
> โปรเจกต์ควรมี unit test ที่รันเร็วจำนวนมาก, integration test จำนวนน้อยกว่า, และ UI test เพียงเล็กน้อย
- Unit test (ฐานล่าง): เร็ว ต้นทุนต่ำ และควรมีจำนวนมากที่สุด
- Integration test (ส่วนกลาง): ใช้ตรวจสอบการทำงานร่วมกันระหว่างคอมโพเนนต์
- UI/E2E test (ส่วนบน): ช้าและแตกหักง่าย จึงควรมีให้น้อยที่สุด
- เป็นโมเดลกลยุทธ์การทดสอบที่ Mike Cohn แนะนำไว้ใน Succeeding with Agile
33. พาราด็อกซ์ของยาฆ่าแมลง (Pesticide Paradox)
> เมื่อรันทดสอบชุดเดิมซ้ำๆ ประสิทธิภาพของมันจะลดลงตามเวลา
- เพราะบั๊กที่การทดสอบเดิมจับได้ถูกจับไปหมดแล้ว จึงต้องเพิ่ม test case ใหม่ๆ อย่างต่อเนื่อง
- จำเป็นต้องทบทวนและอัปเดตชุดการทดสอบอย่างสม่ำเสมอ
34. กฎวิวัฒนาการของซอฟต์แวร์ของ Lehman (Lehman's Laws of Software Evolution)
> ซอฟต์แวร์ที่สะท้อนโลกความเป็นจริงย่อมต้องวิวัฒนาการ และวิวัฒนาการนั้นมีข้อจำกัดที่คาดการณ์ได้
- ซอฟต์แวร์ประเภท E-type (ที่สะท้อนโลกความเป็นจริง) จำเป็นต้องมีการเปลี่ยนแปลงอย่างต่อเนื่องหากจะยังถูกใช้งาน
- ทุกครั้งที่มีการเปลี่ยนแปลง ความซับซ้อนจะเพิ่มขึ้น และหากไม่จัดการอย่างจริงจัง คุณภาพจะลดลง
35. กฎของ Sturgeon (Sturgeon's Law)
> 90% ของทุกสิ่งนั้นไร้ประโยชน์
- Theodore Sturgeon เสนอแนวคิดนี้เพื่อตอบโต้คำวิจารณ์วรรณกรรม SF
- ใช้กับซอฟต์แวร์ได้เช่นกัน: ในบรรดาโค้ด เครื่องมือ และเฟรมเวิร์กส่วนใหญ่ สิ่งที่ยอดเยี่ยมจริงๆ มีอยู่เพียงส่วนน้อย
- จึงควรรักษามาตรฐานด้านคุณภาพให้สูง และโฟกัสกับ 10% ที่มีคุณค่า
Scale
36. กฎของ Amdahl (Amdahl's Law)
> การเพิ่มความเร็วจากการทำงานแบบขนานถูกจำกัดด้วยสัดส่วนของงานที่ไม่สามารถทำแบบขนานได้
- หาก 5% ของโปรแกรมต้องทำแบบลำดับ ต่อให้เพิ่มโปรเซสเซอร์มากแค่ไหน ความเร็วสูงสุดตามทฤษฎีก็อยู่ที่ 20 เท่า
- การตระหนักถึงข้อจำกัดของ parallelization และลด คอขวดแบบลำดับ จะมีประสิทธิภาพมากกว่า
- Gene Amdahl เสนอไว้ในปี 1967
37. กฎของ Gustafson (Gustafson's Law)
> เราสามารถบรรลุการเพิ่มความเร็วอย่างมากในการประมวลผลแบบขนานได้ด้วยการเพิ่มขนาดของปัญหา
- เป็น มุมมองเสริม ต่อกฎของ Amdahl: สำหรับปัญหาที่ขยายขนาดได้ ไม่ใช่ปัญหาคงที่ การเพิ่มโปรเซสเซอร์ย่อมได้ผล
- ในงานอย่างการประมวลผล Big Data หรือการจำลองทางวิทยาศาสตร์ ทรัพยากรที่มากขึ้นช่วยแก้ ปัญหาที่ใหญ่ขึ้น ได้
38. กฎของ Metcalfe (Metcalfe's Law)
> มูลค่าของเครือข่ายแปรผันตามกำลังสองของจำนวนผู้ใช้
- ถ้ามีผู้ใช้ 10 คน มูลค่าจะเพิ่มเป็น 100 หน่วย; ถ้ามี 100 คน จะเพิ่มเป็น 10,000 หน่วย
- เป็นพื้นฐานเชิงทฤษฎีของ network effect ในโซเชียลเน็ตเวิร์ก เมสเซนเจอร์ มาร์เก็ตเพลส ฯลฯ
- Robert Metcalfe เสนอแนวคิดนี้เพื่ออธิบายคุณค่าของเทคโนโลยี Ethernet
การออกแบบ (Design)
39. หลักการ DRY (Don't Repeat Yourself)
> ความรู้ทุกอย่างควรมีเพียงการแสดงออกเดียวที่ชัดเจน เป็นเอกเทศ และเชื่อถือได้
- ไม่ได้รวมแค่การซ้ำของโค้ด แต่รวมถึง ความรู้ ลอจิก และข้อมูลที่ซ้ำกัน ด้วย
- ความซ้ำซ้อนทำให้เวลามีการเปลี่ยนแปลงต้องแก้หลายจุดพร้อมกัน จึงเป็นสาเหตุของ บั๊กและความไม่สอดคล้องกัน
- Andy Hunt และ Dave Thomas วางหลักนี้ไว้ใน The Pragmatic Programmer
40. หลักการ KISS (Keep It Simple, Stupid)
> การออกแบบและระบบควรเรียบง่ายให้มากที่สุดเท่าที่จะเป็นไปได้
- ความซับซ้อนเพิ่มต้นทุนในการทำความเข้าใจ การบำรุงรักษา และการดีบัก
- วิธีแก้ที่เรียบง่าย มักมีประสิทธิภาพกว่าในกรณีส่วนใหญ่ และมีโอกาสเกิดข้อบกพร่องต่ำกว่า
- มีที่มาจากหลักการออกแบบที่กองทัพเรือสหรัฐเสนอไว้ในทศวรรษ 1960
41. หลักการ SOLID (SOLID Principles)
> แนวทางหลัก 5 ข้อเพื่อยกระดับการออกแบบซอฟต์แวร์
- S — หลักการรับผิดชอบเดียว (Single Responsibility): คลาสควรเปลี่ยนเพียงด้วยเหตุผลเดียว
- O — หลักการเปิด-ปิด (Open-Closed): ควรเปิดให้ขยาย แต่ปิดต่อการแก้ไข
- L — หลักการแทนที่ของ Liskov: subtype ควรแทนที่ supertype ได้
- I — หลักการแยกอินเทอร์เฟซ: client ไม่ควรต้องพึ่งพาอินเทอร์เฟซที่ไม่ได้ใช้งาน
- D — หลักการกลับทิศการพึ่งพา: โมดูลระดับบนไม่ควรพึ่งพาโมดูลระดับล่าง แต่ควรพึ่งพา abstraction
- Robert C. Martin วางหลักการนี้ และ Michael Feathers เป็นผู้ตั้งชื่อย่อว่า SOLID
42. กฎของ Demeter (Law of Demeter)
> อ็อบเจ็กต์ควรสื่อสารเฉพาะกับเพื่อนที่ใกล้ชิดโดยตรง และควรหลีกเลี่ยงการสื่อสารกับอ็อบเจ็กต์แปลกหน้าโดยตรง
- เป็นหลักการที่บอกว่าควรหลีกเลี่ยง การเรียกแบบ chain เช่น
a.getB().getC().doSomething() - ช่วยลด coupling และเสริม encapsulation เพื่อลดขอบเขตผลกระทบเมื่อมีการเปลี่ยนแปลง
- เรียกอีกอย่างว่า "หลักการของความรู้น้อยที่สุด"
43. หลักการสร้างความประหลาดใจให้น้อยที่สุด (Principle of Least Astonishment)
> ซอฟต์แวร์และอินเทอร์เฟซควรทำงานในแบบที่ทำให้ผู้ใช้และนักพัฒนาคนอื่นประหลาดใจน้อยที่สุด
- ฟังก์ชัน API และ UI ควรมี พฤติกรรมที่คาดเดาได้ ทั้งในชื่อและคอนเวนชัน
- ถ้าฟังก์ชัน
delete()แท้จริงแล้วแค่ archive ก็จะสร้างความประหลาดใจ → ถือเป็นข้อบกพร่องด้านการออกแบบ - พฤติกรรมที่ไม่เป็นไปตามสัญชาตญาณนำไปสู่บั๊กและความผิดพลาดของผู้ใช้
44. YAGNI (You Aren't Gonna Need It)
> อย่าเพิ่มฟีเจอร์ก่อนที่จะจำเป็นต้องใช้
- เป็นหลักการสำคัญของ Extreme Programming (XP) ที่ Ron Jeffries เสนอในช่วงปลายทศวรรษ 1990
- หากเขียนโค้ดเพียงเพราะ "อาจต้องใช้ในอนาคต" ก็จะก่อให้เกิด การออกแบบเกินจำเป็น และภาระในการบำรุงรักษา
- การปฏิบัติตาม YAGNI ต้องอาศัย ความมั่นใจ ในการรีแฟกเตอร์ (เช่น test coverage ที่ดี, CI)
- หากตอนนี้ต้องการเพียงการ export JSON ก็ให้ทำแค่ JSON ส่วน XML/YAML ค่อยเพิ่มเมื่อมีความต้องการ
การตัดสินใจ (Decisions)
45. ผลของ Dunning-Kruger (Dunning-Kruger Effect)
> ยิ่งรู้น้อยเกี่ยวกับบางเรื่อง ก็ยิ่งมีแนวโน้มมั่นใจมากขึ้น
- เป็นปรากฏการณ์ที่นักพัฒนามือใหม่ประเมินความยากของระบบซับซ้อนต่ำเกินไป หรือผู้เชี่ยวชาญกลับถ่อมตนต่อความรู้ของตนเอง
- การเพิ่ม ความแม่นยำของการรับรู้ตนเอง ผ่าน code review, mentoring และการเรียนรู้อย่างต่อเนื่องเป็นสิ่งสำคัญ
46. มีดโกนของ Hanlon (Hanlon's Razor)
> อย่าอธิบายสิ่งที่อธิบายได้ด้วยความโง่เขลาหรือความสะเพร่า ว่าเกิดจากความมุ่งร้าย
- ก่อนจะตีความโค้ดแย่ๆ หรือการตัดสินใจผิดพลาดของเพื่อนร่วมงานว่าเป็นการขัดขวางโดยเจตนา ควรพิจารณา ความไม่รู้ ความผิดพลาด หรือการขาดเวลา ก่อน
- เป็นพื้นฐานของความไว้วางใจและการสื่อสารเชิงสร้างสรรค์ในทีม
47. มีดโกนของ Occam (Occam's Razor)
> คำอธิบายที่เรียบง่ายที่สุดมักเป็นคำอธิบายที่ถูกต้องที่สุด
- เวลาดีบัก ควรตรวจสอบ ความเป็นไปได้ที่ง่ายที่สุด ก่อน แทนที่จะเริ่มจากสาเหตุที่ซับซ้อน
- ในการออกแบบสถาปัตยกรรมเช่นกัน ควรพิจารณาวิธีแก้ที่เรียบง่ายก่อนเพิ่ม abstraction layer ที่ไม่จำเป็น
48. ความผิดพลาดจากต้นทุนจม (Sunk Cost Fallacy)
> แนวโน้มที่จะยึดติดกับทางเลือกที่ขาดทุนต่อไป เพียงเพราะได้ลงทุนเวลา หรือพลังงานไปแล้ว
- เช่น แม้ฟีเจอร์ที่พัฒนามา 6 เดือนจะไปผิดทาง ก็ยัง ตัดใจทิ้งไม่ได้เพราะเสียดายเวลาที่ลงทุนไป
- การตัดสินใจที่ถูกต้องควรยึดตาม คุณค่าในอนาคต ไม่ใช่การลงทุนในอดีต
49. แผนที่ไม่ใช่อาณาเขตจริง (The Map Is Not the Territory)
> สิ่งที่ใช้แทนความจริง (โมเดล) ไม่ใช่ตัวความจริงเอง
- UML diagram, เอกสารสถาปัตยกรรม, data model ฯลฯ เป็นเพียง การประมาณของความเป็นจริง
- ไม่ควรเชื่อโมเดลอย่างงมงาย แต่ต้องสังเกตพฤติกรรมของระบบจริงและอัปเดตโมเดลอยู่เสมอ
50. อคติยืนยันความเชื่อ (Confirmation Bias)
> แนวโน้มที่จะชอบข้อมูลที่สนับสนุนความเชื่อหรือไอเดียเดิมของตน
- เป็นกับดักของการเลือกเก็บเฉพาะข้อมูลที่เข้าข้าง tech stack หรือการตัดสินใจด้านการออกแบบที่ตัวเองเลือก
- หัวใจของการตัดสินใจอย่างสมดุลคือการ ค้นหาหลักฐานที่ขัดแย้งอย่างจริงจัง และเปิดรับมุมมองที่หลากหลาย
51. Hype Cycle และกฎของ Amara (The Hype Cycle & Amara's Law)
เรามักประเมินผลกระทบระยะสั้นของเทคโนโลยีสูงเกินจริง และประเมินอิทธิพลระยะยาวต่ำเกินไป
- Hype Cycle ของ Gartner: การจุดประกายเทคโนโลยี → จุดสูงสุดของความคาดหวังเกินจริง → หุบเขาแห่งความผิดหวัง → ทางลาดแห่งการรู้แจ้ง → ระยะคงตัวของผลิตภาพ
- เมื่อนำเทคโนโลยีใหม่มาใช้ (เช่น บล็อกเชน, AI ฯลฯ) ไม่ควรถูกกระแสความร้อนแรงระยะสั้นพาไป แต่ควรประเมิน ความใช้ได้จริงในระยะยาว
52. Lindy Effect
สิ่งที่ถูกใช้งานมายาวนาน ยิ่งมีแนวโน้มว่าจะยังถูกใช้ต่อไปในอนาคต
- เทคโนโลยีที่ ถูกใช้งานมาหลายสิบปี อย่าง UNIX, SQL และภาษา C มีแนวโน้มสูงว่าจะอยู่รอดต่อไปได้อีกนาน
- เป็นฐานคิดเชิงทฤษฎีเมื่อต้องเลือกเทคโนโลยีที่ผ่านการพิสูจน์แล้วแทนเฟรมเวิร์กใหม่
- Nassim Nicholas Taleb ทำให้แนวคิดนี้เป็นที่แพร่หลายใน Antifragile
53. การคิดแบบปฐมหลัก (First Principles Thinking)
วิธีคิดที่แยกปัญหาซับซ้อนออกเป็นองค์ประกอบพื้นฐานที่สุด แล้วสร้างกลับขึ้นมาใหม่จากจุดนั้น
- ตัดทิ้งแนวปฏิบัติและสมมติฐานเดิม ๆ แล้วหาทางออกโดยเริ่มจาก ความจริงระดับรากฐาน
- เป็นที่รู้จักจากกรณีที่ Elon Musk นำไปใช้เพื่อลดต้นทุนจรวดของ SpaceX
- ในการออกแบบระบบที่ซับซ้อน ควรระวังวิธีคิดแบบ “เดิม ๆ เขาก็ทำกันอย่างนั้น”
54. การคิดแบบกลับทาง (Inversion)
วิธีแก้ปัญหาด้วยการสมมติผลลัพธ์ตรงกันข้าม แล้วให้เหตุผลย้อนกลับ
- แทนที่จะคิดว่า “จะทำอย่างไรจึงจะสำเร็จ” ให้คิดก่อนว่า “จะทำอย่างไรจึงจะล้มเหลว” เพื่อระบุปัจจัยเสี่ยง
- เป็นฐานคิดเชิงทฤษฎีของการวิเคราะห์โหมดความล้มเหลว (Failure Mode Analysis) และการทำ Pre-mortem
- เป็น mental model ที่ Charlie Munger ใช้บ่อย
55. หลักการพาเรโต / กฎ 80/20 (Pareto Principle)
ปัญหา 80% เกิดจากสาเหตุ 20%
- บั๊ก 80% ทั้งหมดมัก กระจุกตัวอยู่ในโค้ด 20%
- การทุ่มทรัพยากรไปที่ 20% ที่ส่งผลมากที่สุด เป็นกลยุทธ์การจัดสรรทรัพยากรที่มีประสิทธิภาพ
- มีที่มาจากหลักการที่ Vilfredo Pareto สังเกตจากการกระจายการถือครองที่ดินในอิตาลี
56. กฎของ Cunningham (Cunningham's Law)
วิธีที่ดีที่สุดในการได้คำตอบที่ถูกต้องบนอินเทอร์เน็ต ไม่ใช่การตั้งคำถาม แต่คือการโพสต์คำตอบที่ผิด
- ผู้คนมักมีส่วนร่วมกับการ แก้ไขข้อมูลที่ผิด มากกว่าการตอบคำถาม
- เป็นกฎที่ตั้งชื่อตาม Ward Cunningham (ผู้คิดค้น Wiki) แต่จริง ๆ แล้ว Steven McGeady เป็นผู้ตั้งชื่อนี้
- เป็นข้อสังเกตที่นำไปใช้กับการทำเอกสารหรือการแบ่งปันความรู้ในชุมชนโอเพนซอร์สได้
2 ความคิดเห็น
ถ้า vibe coding มันก็ดีอยู่ในตอนนี้ แต่สุดท้ายก็ดูเหมือนว่าจะย้อนกลับมาส่งผลกรรมกับเรา...
ความคิดเห็นใน Hacker News
ฉันเกลียดวลี "การปรับแต่งประสิทธิภาพเร็วเกินไป คือรากเหง้าของความชั่วร้ายทั้งปวง" เป็นพิเศษ ประโยคนี้มาจากบริบทของปี 1974 ซึ่งมีสมมติฐานต่างจากปัจจุบัน ตอนนั้นการ optimize ใกล้เคียงกับการเขียน assembly และนับจำนวน cycle แต่ทุกวันนี้ประสิทธิภาพส่วนใหญ่เป็นปัญหาของ การเลือกสถาปัตยกรรม จึงต้องคิดตั้งแต่ต้น คำแนะนำให้ใช้ profiling เพื่อจับบั๊กด้านประสิทธิภาพอย่าง O(n²) ที่เกิดขึ้นโดยไม่ตั้งใจยังคงใช้ได้ แต่พอค่าใช้จ่ายของ abstraction กลายเป็นคอขวดแล้ว ก็มักลงเอยด้วยการแปะ cache กับ parallelism เพิ่มเข้าไป จนระบบซับซ้อนขึ้นและช้าลงกว่าเดิม ตอนนี้ฉันมองว่าการ optimize ช้าเกินไปก็แย่พอๆ กับการ optimize เร็วเกินไป หรืออาจแย่กว่าเสียอีก
ฉันเสียดายที่ไม่มี Curly's Law ตัวแปรควรมี ความหมายเดียว เท่านั้น ไม่ควรเก็บค่าจากคนละโดเมนตามสถานการณ์ หรือทำหน้าที่สองอย่างพร้อมกัน อุปมาแบบ "เป็นทั้งน้ำยาเคลือบพื้นและท็อปปิงของหวาน" นี่ตรงมาก
ฉันรู้สึกว่าพอรวบรวม "กฎ" ของซอฟต์แวร์พวกนี้ไว้ด้วยกัน มันมี ความขัดแย้งภายใน กันมากเกินไป สุดท้ายเลยหยิบประโยคไหนมาก็ได้เพื่อสนับสนุนสิ่งที่ตัวเองอยากพูด เรื่องที่ยากจริงคือการรู้ว่าเมื่อไรควรละเมิดกฎข้อไหน และทำไมถึงต้องละเมิดมัน
ถ้าจะพูดเล่นเรื่องกฎวิศวกรรมซอฟต์แวร์ฉบับปี 2026 ฉันว่าเว็บทุกแห่งจะถูก vibe coding ด้วย Claude Opus ผลคือพื้นหลังจะออกโทนครีมคล้าย Anthropic ฟอนต์กับน้ำหนักตัวอักษรจะถูกผสมกันเกินเหตุเหมือนคนเพิ่งหัดออกแบบเรียนรู้เรื่อง typography มาใหม่ๆ จะมี card UI ล้นไปหมด และชอบทำกรอบสีมนๆ แค่ด้านเดียวของการ์ดเป็นแพตเทิร์นซ้ำๆ
ฉันคิดว่าควรใส่ Boyd's Law of Iteration ด้วย เวลารับมือกับความซับซ้อน หลายครั้ง การวนซ้ำอย่างรวดเร็ว ให้ผลดีกว่าการวิเคราะห์เชิงลึกเสียอีก และยิ่งน่าประทับใจเมื่อคิดว่า Boyd คือคนที่สร้าง OODA loop
ฉันคิดว่าในบรรดาคอมเมนต์ที่ถูกลบ มี เมตากฎที่ดีที่สุด สำหรับบทความนี้อยู่ ข้อความนั้นคือ "กฎวิศวกรรมซอฟต์แวร์ทุกข้อจะถูกเข้าใจผิดทันที และถูกนำไปใช้อย่างไม่วิพากษ์วิจารณ์ในแบบที่ผู้เขียนต้นฉบับต้องช็อก" พอเห็นพฤติกรรมของ LLM ที่ขาดบริบทสำคัญ ก็ยิ่งเข้าใจว่าทำไม สุดท้ายแล้วการบีบอัดภูมิปัญญาและประสบการณ์หลายสิบปีให้เหลือเป็น คำคมบรรทัดเดียว มันมีขีดจำกัด
ถ้าจะ vibe coding เว็บไซต์ที่เป็นแค่ "รายการกฎวิศวกรรมซอฟต์แวร์" ทั้งเว็บ ฉันก็อยากถามว่าการไม่ทำเป็นหน้า Wikipedia ไปเลยนั้นมันผิดกฎข้อไหน
ฉันหวังว่าเรื่องแบบนี้จะเป็น ความรู้พื้นฐาน ถึงขั้นเป็นข้อกำหนดในการสมัครงานเลย เพราะมันดูเป็นสิ่งที่ทุกคนควรรู้
ถึงจะไม่ใช่กฎเฉพาะของซอฟต์แวร์ ฉันก็มักสอน Chesterton's Fence ให้เด็กฝึกงานกับพนักงานใหม่ก่อนเป็นอย่างแรก
ฉันรู้สึกว่า กฎการอนุรักษ์ความซับซ้อนของ Tesler ให้ภาพเข้าใจได้ทันทีจากตัวประโยคเอง มันบอกว่าแอปพลิเคชันทุกตัวมีความซับซ้อนประจำตัวที่เอาออกไม่ได้ มีได้แค่ย้ายที่เท่านั้น แต่พออ่านคำอธิบายต่อ มันกลับเหมือนย่อเหลือแค่คำแนะนำธรรมดาว่าอย่าทำให้ผู้ใช้ลำบากเกินไป ซึ่งทำให้ความน่าสนใจลดลงหน่อย ผู้ใช้ก็ยังต้องเผชิญกับความซับซ้อนในระดับที่จำเป็นอยู่ดี และถ้าลดแบบไม่คิดก็อาจกลายเป็นของเล่นที่ยืดหยุ่นน้อย ดังนั้นเวลาฉัน refactor ฉันจึงเห็นว่าการจำไว้ว่าพอทำให้ส่วนหนึ่งง่ายลง อีกส่วนหนึ่งอาจซับซ้อนขึ้นนั้นมีประโยชน์กว่า