ฉันอยากจะขอให้คนที่มีประสบการณ์ในการทำงานกับระบบในระดับ Visual Studio: อะไรที่ทำให้พวกเขาช้า? มันเป็นชั้น ๆ บนเลเยอร์ของ abstractions ที่จำเป็นในการรักษา codebase ให้อยู่ในขีดความสามารถของมนุษย์หรือไม่? เป็นจำนวนรหัสที่ต้องใช้ในการทำงานหรือไม่ มันเป็นแนวโน้มที่ทันสมัยต่อวิธีการประหยัดเวลาโปรแกรมเมอร์ที่ค่าใช้จ่าย (เหลือเชื่อใหญ่) ในรอบนาฬิกา / แผนกการใช้หน่วยความจำ?
ฉันคิดว่าคุณคาดเดาจำนวนหนึ่งของพวกเขา แต่ฉันต้องการที่จะเสนอสิ่งที่ฉันคิดว่าเป็นปัจจัยที่ยิ่งใหญ่ที่สุดที่ได้ทำงานใน codebase ขนาดใหญ่พอสมควร (ไม่แน่ใจว่ามันใหญ่เท่า Visual Studio - หรือไม่ ประเภทและประมาณหนึ่งพันปลั๊กอิน) ประมาณ 10 ปีและสังเกตปรากฏการณ์เกิดขึ้น
นอกจากนี้ยังเป็นที่ถกเถียงกันน้อยลงเนื่องจากไม่ได้มีคุณลักษณะแบบ API หรือภาษาหรืออะไรทำนองนั้น สิ่งเหล่านั้นเกี่ยวข้องกับ "ค่าใช้จ่าย" ซึ่งสามารถนำไปสู่การอภิปรายมากกว่า "การใช้จ่าย" และฉันต้องการที่จะมุ่งเน้นไปที่ "การใช้จ่าย"
การประสานงานและมรดกที่หลวม
สิ่งที่ฉันสังเกตคือการประสานงานที่หลวมและมรดกที่ยาวนานมีแนวโน้มที่จะนำไปสู่การสะสมของเสียจำนวนมาก
ตัวอย่างเช่นฉันพบโครงสร้างการเร่งความเร็วประมาณหนึ่งร้อยแห่งใน codebase นี้โดยส่วนใหญ่จะซ้ำซ้อนกัน
เราต้องการต้นไม้ KD สำหรับเร่งเครื่องยนต์ฟิสิกส์อีกอันหนึ่งสำหรับเครื่องยนต์ฟิสิกส์ใหม่ที่มักจะทำงานคู่ขนานกับต้นไม้เก่าเรามีการใช้งานหลายสิบแปดสำหรับอัลกอริทึมตาข่ายต่างๆต้นไม้ KD อื่นสำหรับการแสดงผล การเลือกและอื่น ๆ เป็นต้นทั้งหมดนี้เป็นโครงสร้างต้นไม้ขนาดใหญ่ที่ใช้เพื่อเร่งการค้นหา แต่ละคนสามารถใช้หน่วยความจำหลายร้อยเมกะไบต์ถึงกิกะไบต์สำหรับการป้อนข้อมูลขนาดเฉลี่ยมาก พวกเขาไม่ได้อินสแตนซ์เสมอและใช้ตลอดเวลา แต่ในเวลาใดก็ตาม 4 หรือ 5 ของพวกเขาอาจอยู่ในหน่วยความจำพร้อมกัน
ตอนนี้สิ่งเหล่านี้กำลังเก็บข้อมูลเดียวกันที่แน่นอนเพื่อเร่งการค้นหา คุณสามารถจินตนาการได้ว่ามันเหมือนกับฐานข้อมูลเก่าแบบอะนาล็อกซึ่งเก็บฟิลด์ทั้งหมดของมันไว้ในแผนที่ / พจนานุกรม / B + ต้นไม้ซ้ำซ้อนกว่า 20 รายการพร้อมกันจัดระเบียบโดยใช้คีย์เดียวกันและค้นหาทั้งหมดตลอดเวลา ตอนนี้เราใช้หน่วยความจำและประมวลผล 20 เท่า
นอกจากนี้เนื่องจากความซ้ำซ้อนจึงมีเวลาน้อยที่จะเพิ่มประสิทธิภาพของพวกเขาด้วยป้ายราคาการบำรุงรักษาที่มาพร้อมกับที่และแม้ว่าเราจะทำมันก็จะมีเพียง 5% ของผลกระทบที่มันจะนึกคิด
ทำให้เกิดปรากฏการณ์นี้คืออะไร? การประสานงานที่หลวมเป็นสาเหตุอันดับหนึ่งที่ฉันเห็น สมาชิกในทีมจำนวนมากมักทำงานในระบบนิเวศที่แยกได้ของพวกเขาพัฒนาหรือใช้โครงสร้างข้อมูลของบุคคลที่สาม แต่ไม่ได้ใช้โครงสร้างเดียวกันสมาชิกคนอื่น ๆ ในทีมใช้แม้ว่าพวกเขาจะซ้ำซ้อนทันทีของข้อกังวลเดียวกัน
อะไรทำให้ปรากฏการณ์นี้ยังคงอยู่ มรดกและความเข้ากันได้เป็นสาเหตุอันดับหนึ่งที่ฉันเห็น เนื่องจากเราจ่ายค่าใช้จ่ายในการปรับใช้โครงสร้างข้อมูลเหล่านี้และโค้ดจำนวนมากขึ้นอยู่กับโซลูชันเหล่านี้จึงมักมีความเสี่ยงที่จะรวมเข้ากับโครงสร้างข้อมูลน้อยลง แม้ว่าโครงสร้างข้อมูลจำนวนมากเหล่านี้จะมีแนวคิดซ้ำซ้อนสูง แต่ก็ไม่ได้ใกล้เคียงกันในการออกแบบอินเตอร์เฟส ดังนั้นการแทนที่มันจะเป็นการเปลี่ยนแปลงครั้งใหญ่และมีความเสี่ยงซึ่งต่างจากการปล่อยให้พวกเขาใช้หน่วยความจำและเวลาในการประมวลผล
ประสิทธิภาพของหน่วยความจำ
โดยทั่วไปการใช้หน่วยความจำและความเร็วมักจะเกี่ยวข้องกับระดับกลุ่มอย่างน้อย คุณมักจะมองเห็นซอฟต์แวร์ที่ช้าโดยวิธีที่หน่วยความจำเพิ่มขึ้น มันไม่เป็นความจริงเสมอไปที่หน่วยความจำมากขึ้นจะนำไปสู่การชะลอตัวเนื่องจากสิ่งที่สำคัญคือหน่วยความจำ "ร้อน" (หน่วยความจำใดที่ถูกเข้าถึงตลอดเวลา - หากโปรแกรมใช้หน่วยความจำ boatload แต่เพียง 1 เมกะไบต์เท่านั้น ถึงเวลาแล้วมันไม่ใช่เรื่องง่ายเลย
ดังนั้นคุณจึงสามารถสังเกตเห็นหมูที่เป็นไปได้จากการใช้หน่วยความจำบ่อยครั้ง หากแอปพลิเคชันใช้หน่วยความจำนับสิบถึงร้อยเมกะไบต์เมื่อเริ่มต้นอาจเป็นไปได้ว่าจะไม่มีประสิทธิภาพมากนัก จำนวนเมกะไบต์อาจดูเล็กมากเมื่อเรามีกิกะไบต์ของ DRAM ในวันนี้ แต่แคช CPU ที่ใหญ่ที่สุดและช้าที่สุดยังคงอยู่ในช่วงเมกะไบต์ที่เลวร้ายที่สุดและเร็วที่สุดยังคงอยู่ในช่วงกิโลไบต์ ด้วยเหตุนี้โปรแกรมที่ใช้ 20 เมกะไบต์เพื่อเริ่มต้นและไม่ทำอะไรเลยจริงๆยังคงใช้หน่วยความจำ "มาก" จากมุมมอง CPU แคชของฮาร์ดแวร์โดยเฉพาะอย่างยิ่งถ้าหน่วยความจำนั้นมีการเข้าถึงหน่วยความจำ 20 เมกะไบต์ทั้งหมดซ้ำ ๆ บ่อยครั้งที่โปรแกรมกำลังทำงาน
วิธีการแก้
สำหรับฉันทางออกคือการหาทีมที่เล็กกว่าและมีการประสานงานกันเพื่อสร้างผลิตภัณฑ์ผู้ที่สามารถติดตาม "การใช้จ่าย" และหลีกเลี่ยง "การซื้อ" รายการเดียวกันซ้ำแล้วซ้ำอีก
ราคา
ฉันจะจุ่มลงในด้าน "ต้นทุน" ที่ถกเถียงกันมากขึ้นเพียงเล็กน้อยที่มีปรากฏการณ์ "การใช้จ่าย" ที่ฉันสังเกตเห็น หากภาษาลงท้ายด้วยแท็กราคาที่หลีกเลี่ยงไม่ได้สำหรับวัตถุ (เช่นภาษาที่ให้ภาพสะท้อนแบบรันไทม์และไม่สามารถบังคับการจัดสรรแบบต่อเนื่องสำหรับชุดของวัตถุ) ป้ายราคานั้นมีราคาแพงในบริบทขององค์ประกอบที่ละเอียดมากเช่น เดี่ยวPixel
หรือBoolean
.
แต่ฉันเห็นซอร์สโค้ดจำนวนมากสำหรับโปรแกรมที่จัดการกับภาระจำนวนมาก (เช่นการจัดการกับหลายแสนถึงล้านครั้งPixel
หรือหลายBoolean
ครั้ง) ซึ่งจ่ายค่าใช้จ่ายในระดับที่ละเอียดมาก
การเขียนโปรแกรมเชิงวัตถุสามารถทำให้รุนแรงขึ้นได้ แต่มันไม่ใช่ค่าใช้จ่ายของ "วัตถุ" ต่อ se หรือแม้แต่ความผิดพลาดของ OOP มันเป็นเพียงการจ่ายค่าใช้จ่ายดังกล่าวในระดับละเอียดขององค์ประกอบเล็ก ๆ ที่จะถูกสร้างขึ้นโดยคนนับล้าน
นั่นคือปรากฏการณ์ "ต้นทุน" และ "การใช้จ่าย" อื่น ๆ ที่ฉันกำลังสังเกต ค่าใช้จ่ายเป็นเพนนี แต่เงินเพิ่มขึ้นถ้าเราซื้อโซดาล้านกระป๋องแยกกันแทนที่จะเจรจากับผู้ผลิตเพื่อซื้อจำนวนมาก
วิธีแก้ปัญหาสำหรับฉันคือการซื้อ "จำนวนมาก" วัตถุมีความสมบูรณ์ดีแม้ในภาษาที่มีป้ายราคาบางเพนนีต่อแต่ละคนโดยมีเงื่อนไขว่าค่าใช้จ่ายนี้จะไม่ถูกจ่ายทีละล้านกว่าครั้งสำหรับการเปรียบเทียบแบบอะนาล็อกของโซดากระป๋อง
การเพิ่มประสิทธิภาพก่อนวัยอันควร
ฉันไม่ชอบคำที่ Knuth เคยใช้ที่นี่เพราะ "การปรับให้เหมาะสมก่อนกำหนด" ไม่ค่อยทำให้โปรแกรมการผลิตในโลกแห่งความเป็นจริงเร็วขึ้น บางคนตีความว่าเป็น "การเพิ่มประสิทธิภาพเร็ว" เมื่อ Knuth มีความหมายมากกว่าเช่น "การปรับให้เหมาะสมโดยปราศจากความรู้ / ประสบการณ์ที่เหมาะสมเพื่อรับรู้ถึงผลกระทบที่แท้จริงต่อซอฟต์แวร์" หากมีสิ่งใดที่มีผลในทางปฏิบัติของการเพิ่มประสิทธิภาพก่อนวัยอันควรที่แท้จริงมักจะเป็นไปได้ที่ซอฟแวร์ให้ช้าลงเนื่องจากการย่อยสลายในการบำรุงรักษาวิธีการที่มีเวลาน้อยที่จะเพิ่มประสิทธิภาพเส้นทางสำคัญที่เรื่องจริงๆ
นี่เป็นปรากฏการณ์สุดท้ายที่ฉันสังเกตเห็นซึ่งนักพัฒนาเข้าถึงการประหยัดเพนนีในการซื้อโซดากระป๋องเดียวไม่เคยถูกซื้ออีกหรือแย่กว่านั้นบ้านกำลังสูญเสียเวลาฉกชิงเพนนี (หรือแย่กว่านั้นเพนนีจินตนาการจาก ไม่เข้าใจคอมไพเลอร์หรือสถาปัตยกรรมของฮาร์ดแวร์) เมื่อมีการใช้เงินไปหลายพันล้านดอลลาร์อย่างสิ้นเปลือง
เวลามี จำกัด มากดังนั้นการพยายามทำให้สัมบูรณ์สมบูรณ์โดยไม่ต้องมีข้อมูลบริบทที่เหมาะสมมักทำให้เราขาดโอกาสในการปรับสถานที่ที่แท้จริงอย่างแท้จริงและดังนั้นในแง่ของผลเชิงปฏิบัติฉันจะบอกว่า "การเพิ่มประสิทธิภาพก่อนกำหนดทำให้ซอฟต์แวร์ช้าลงมาก "
ปัญหาคือมีนักพัฒนาประเภทหนึ่งที่จะใช้สิ่งที่ฉันเขียนไว้ด้านบนเกี่ยวกับวัตถุและพยายามสร้างมาตรฐานการเข้ารหัสที่ห้ามการเขียนโปรแกรมเชิงวัตถุ การเพิ่มประสิทธิภาพที่มีประสิทธิภาพคือการจัดลำดับความสำคัญที่มีประสิทธิภาพและไม่มีค่าอย่างแน่นอนหากเราจมอยู่ในปัญหาการบำรุงรักษา