การใช้ DI / IoC ควรลบคำหลัก“ ใหม่” ที่เกิดขึ้นทั้งหมดหรือไม่


21

การใช้การพึ่งพาการฉีดและผกผันของการควบคุมควรลบการเกิดขึ้นทั้งหมดของnewคำหลัก "" ออกจากรหัสของคุณหรือไม่?

ในคำอื่น ๆ ทุกวัตถุ / การพึ่งพาไม่ว่าจะง่ายหรืออายุสั้นเป็น "ลงทะเบียน" ในภาชนะ IoC ของคุณและฉีดเข้าไปในวิธีการ / ชั้นเรียนที่ต้องใช้พวกเขา?

ถ้าไม่คุณจะวาดเส้นไหนระหว่างการพึ่งพา / วัตถุที่ลงทะเบียนในคอนเทนเนอร์ IoC เทียบกับสิ่งที่ได้รับการสร้าง "ในบรรทัด" เป็นข้อมูลอ้างอิงที่เป็นรูปธรรมผ่านnewคำหลัก?


ฉันมีความคิดแบบเดียวกันตามบรรทัดของ "คือ 'ใหม่' คำ 4 ตัวอักษร?
Michael Easter

คำตอบ:


27

หลีกเลี่ยงความเชื่อ ทำในสิ่งที่รู้สึกถูกต้อง

ฉันชอบที่จะใช้ "ใหม่" สำหรับโครงสร้างข้อมูลที่ไม่มีพฤติกรรม

ถ้าชั้นเรียนมีพฤติกรรมฉันจะดูขอบเขตของพฤติกรรมนั้น ถ้าไร้สัญชาติและไม่มีการพึ่งพาฉันก็โน้มตัวไปสู่ ​​"ใหม่" ฉันเพิ่งเริ่ม refactoring ไปยัง DI เมื่อฉันต้องการเพิ่มการพึ่งพาทรัพยากร stateful (เช่นฐานข้อมูลหรือไฟล์) หรือชั้นอื่น ๆ ที่มีทรัพยากรดังกล่าว


15
+1 สำหรับ "หลีกเลี่ยง dogma" วิธีที่ง่ายเกินไปที่จะตกหลุมพรางของเพียงทำตามการเคลื่อนไหวโดยไม่เข้าใจสิ่งที่เกิดขึ้นหรือที่ควรจะใช้อย่างถูกต้อง
Wayne Molina

@Alex ฉันชอบสิ่งนี้ วิธีการปฏิบัติมาก สนุกพอฉันจะเพิ่มรหัสในคำถามของฉันแสดงการnewพึ่งพา 'ed ในรหัสของตัวเองที่แจ้งคำถามของฉัน มันเป็นคลาสที่เรียบง่ายโดยไม่มีฟังก์ชั่นหรือ "พฤติกรรม" ต่อคุณสมบัติที่เรียบง่ายเท่านั้น
CraigTP

11

ในหนังสือของฉันฉันให้ความแตกต่างระหว่างอันดับเครดิตมีเสถียรภาพและพึ่งพาระเหย เป็นสิ่งสำคัญที่สุดที่จะใช้ DI กับการพึ่งพาที่เปลี่ยนแปลงได้ แต่บ่อยครั้งที่คุณสามารถบรรลุการเชื่อมต่อที่ราบรื่นยิ่งขึ้นด้วยการสรุปและการฉีดการพึ่งพาที่เสถียร

โปรดทราบว่าแอปพลิเคชัน DI ไม่ควรเชื่อถือใน DI Container ในกรณีที่แย่ของมนุษย์ DIมีการใช้งานไม่มีnewคำหลักจะถูกลบออก - พวกเขาจะย้ายไปทางรากองค์ประกอบ

บางคนชอบ DI แย่ของ Poor Man มากกว่า DI Containers ค่าใช้จ่ายในการบำรุงรักษาอาจสูงขึ้น แต่คุณจะได้รับความปลอดภัยในเวลาคอมไพล์ อย่างที่ฉันเพิ่งได้ยิน Dan North พูดว่า: " newis the new new" :)

สิ่งนี้มีความหมายโดยง่ายกว่าการใช้ Composition Root กับ DI Container มันก็แค่มีnewคำสั่งซ้อนกันจำนวนมาก


ทำเครื่องหมายเพื่อขยายความคิดเห็น Twitterของฉันเล็กน้อยโปรแกรมเมอร์เป็นสถานที่ที่เหมาะสมสำหรับคำถามเชิงแนวคิดและไวท์บอร์ดที่ไม่ได้เกี่ยวข้องกับข้อผิดพลาดเฉพาะในการนำไปใช้
อดัมเลียร์

3
Stack Overflow มีคำถามมากกว่า 2,000 ข้อในแท็กการพึ่งพาและส่วนใหญ่มีลักษณะเช่นนี้ โปรแกรมเมอร์มี 23 คำถามในแท็กเดียวกัน จากตัวเลขเหล่านี้ผู้พัฒนาควรจะมีโอกาสที่ดีที่สุดในการรับคำตอบของคำถามเช่นนี้หรือไม่
Mark Seemann

1
คำถามมากมายที่เขียนลงวันที่ล่วงหน้าโปรแกรมเมอร์อย่างสมบูรณ์ ไซต์นี้สร้างขึ้นเพื่อนำคำถามเชิงแนวคิดออกจาก SO และให้พวกเขามีบ้านโดยเฉพาะ และเรายังคงเติบโต เป็นงานที่อยู่ระหว่างดำเนินการ แต่คำถามที่นึกคิดว่าไม่เกี่ยวข้องกับปัญหาการใช้งานเฉพาะจะได้รับการย้ายที่นี่ เราทำสิ่งที่เราทำได้ในระหว่างนี้
อดัมเลียร์

3

"ใหม่" ไม่ใช่คำหลักที่ต้องห้าม กฎส่วนตัวของฉัน:

"บริการ" ทั้งหมด (ฉันเรียกบริการที่ออกแบบมาเพื่อให้วิธีการหนึ่งหรือหลายวิธีที่เกี่ยวข้องกับสิ่งหนึ่งและสิ่งเดียวเท่านั้นตัวอย่างเช่น: เข้าถึงฐานข้อมูลเรียก / อัปเดตข้อมูลที่เกี่ยวข้องกับโดเมนที่กำหนด) ลงทะเบียนในคอนเทนเนอร์ IOC ไม่ควรมีคลาสใดในการตัดสินใจเกี่ยวกับวิธีการขอรับบริการที่จำเป็นต้องใช้ ดังนั้นเมื่อใดก็ตามที่คุณต้องการใช้บริการที่มีอยู่คุณควรกำหนดค่าคลาสและคอนเทนเนอร์ IOC ของคุณเพื่อให้บริการแก่คุณ ลองนึกภาพว่าคุณไม่ทราบว่าการใช้งานของคุณอาจเป็นบริการเว็บคุณไม่สนใจ

ต้องสร้าง bean หรือโมเดลทั้งหมดด้วยคำหลัก "ใหม่" หรือกับโรงงานที่ลงทะเบียน IOC เมื่อฉันต้องการให้เปิดใช้คุณสมบัติเริ่มต้นบางอย่าง นอกจากนี้ยังมีกรณีพิเศษของคลาสยูทิลิตี้ที่มีวิธีการคงที่เท่านั้น (ตัวอย่างเช่น: บริการสาธารณูปโภคทางคณิตศาสตร์) หากพวกเขาเป็นแบบสแตนด์อโลนโดยสมบูรณ์และไม่จำเป็นต้องเชื่อมต่อฐานข้อมูลหรือบริการที่ลงทะเบียน IOC อื่นฉันจะปล่อยให้พวกเขาออกจาก IOC และพวกเขาจะถูกเรียกว่าแบบคงที่ อย่างไรก็ตามหากคลาสดังกล่าวต้องการใช้บริการที่ลงทะเบียน IOC ที่มีอยู่ฉันจะเปลี่ยนเป็นคลาสซิงเกิลตันและลงทะเบียนใน IOC


2

ฉันแค่อยากจะเพิ่มคำตอบที่มีอยู่ที่ถูกนำขึ้นมา earler newเป็นอย่างดีในการสร้างวัตถุที่เป็นวัตถุที่มีค่าบริสุทธิ์ (เช่นมีคุณสมบัติเท่านั้น / getters / setters) ดูบล็อกทดสอบของ Googleสำหรับรายละเอียดเพิ่มเติม


+1 สำหรับลิงก์ จุดที่ 9 ในการโพสต์บล็อกนั้นตอบคำถามและให้ความแตกต่างอย่างจริงจังระหว่างสิ่งที่ควรและไม่ควรเป็นnew'ed
CraigTP

1

ชัดเจนขึ้นอยู่กับภาษาที่คุณใช้ หากภาษาของคุณบังคับให้คุณใช้อ็อบเจกต์เพื่อแสดงทั้งออบเจ็กต์จริงและเรคคอร์ด (value object, structs) ดังนั้นคำตอบก็น่าจะไม่ใช่

การพูดถึงวัตถุ "ของจริง" ล้วนๆไม่มีอะไรผิดปกติกับการสร้างอินสแตนซ์อย่างชัดเจน อย่างไรก็ตามสิ่งที่คุณต้องคำนึงถึงคือทุกชั้นเรียนควรปฏิบัติตามหลักการความรับผิดชอบเดียว มันไม่ควรจะเป็นความรับผิดชอบของชั้นเรียนที่จะเลือกผู้ดำเนินการของบริการที่อาศัย อย่างไรก็ตามมีชั้นเรียนที่มีความรับผิดชอบอย่างมากเช่นการให้บริการแก่ผู้ดำเนินการบางอย่าง IoC อาจเป็นคลาสดังกล่าว ในความเป็นจริงโรงงานประเภทใดเป็นคลาสดังกล่าว

ดังนั้นเพื่อสรุป: เฉพาะคลาสดังกล่าวเท่านั้นที่ควรสร้างอินสแตนซ์วัตถุโดยตรงซึ่งเป็นความรับผิดชอบของมันคือการเลือกคลาสที่จะยกตัวอย่าง
คุณอาจพบว่าเกณฑ์เหล่านี้มีประโยชน์: http://en.wikipedia.org/wiki/GRASP_(object-oriented_design)#Creator


1

หนึ่งคำ: ไม่

คำเพิ่มเติม: การฉีดขึ้นอยู่กับว่า เป็นวิธีการที่คุณแนะนำทรัพยากรที่วัตถุอื่นขึ้นอยู่กับ แต่ไม่ควรทราบรายละเอียดที่ซับซ้อนของจากแหล่งอื่น การใช้ DI ไม่ได้หมายความว่าไม่มีสิ่งใดในโปรแกรมของคุณที่ควรรู้วิธีสร้างวัตถุอื่น ๆ ในความเป็นจริงฉันวางตัวว่าเป็นไปไม่ได้อย่างสูงสำหรับโปรแกรมที่ไม่สำคัญเพื่อหลีกเลี่ยงคำหลัก "ใหม่" (หรือทางเลือกที่ใช้การสะท้อน) ทั้งหมด อย่างไรก็ตาม DI หมายความว่าวัตถุที่ไม่ควรรู้วิธีสร้างวัตถุที่ซับซ้อนซึ่งต้องมีการพึ่งพาจำนวนมากที่จะจับคู่วัตถุนี้กับวัตถุอื่นอย่างแน่นหนาไม่ควรมีความรู้ทั้งหมดที่มีอยู่อย่างแน่นหนา

ฉันจะศึกษาทฤษฎีหลักสองประการของการออกแบบซอฟต์แวร์ O / O, GRASP และ SOLID GRASP จะบอกให้คุณศึกษาวัตถุประสงค์ของวัตถุนั้นและถามตัวเองว่า "วัตถุนี้ควรจะรับผิดชอบในการสร้างวัตถุใหม่ประเภทอื่นหรือไม่นี่เป็นส่วนหนึ่งของ 'ลักษณะงาน' ของวัตถุนี้หรือไม่? SOLID ไปอีกขั้นหนึ่ง: "S" ย่อมาจาก "Single Responsibility Principle" ซึ่งระบุไว้อย่างชัดเจนว่าวัตถุควรมีงานหนึ่งงานและควรเป็นวัตถุเดียวในโปรแกรมที่ทำงานเฉพาะนั้น

ดังนั้นโดยทั่วไป GRASP จะแนะนำให้คุณดูคลาสที่มีอยู่ซึ่งการสร้างวัตถุใหม่เหล่านี้และค้นหาสิ่งที่งานการสร้างวัตถุนี้เหมาะกับสิ่งที่วัตถุทำอยู่แล้วในขณะที่รักษาระดับ "การติดต่อ" ที่คุณต้องการ SOLID จะบอกคุณว่าการทำงานร่วมกันเป็นกุญแจสำคัญ งานในการสร้างวัตถุเหล่านี้ควรมอบให้กับโรงงานที่ควรฉีดเข้าไปในชั้นเรียนของคุณ ฉันคิดว่าคุณจะพบว่าเมื่อความซับซ้อนของโปรแกรมของคุณเพิ่มขึ้นอย่างต่อเนื่องการยึดมั่นกับวิธีการเหล่านี้อย่างใดอย่างหนึ่งด้วยความเต็มใจที่จะสร้างใหม่จะส่งผลให้มีสถาปัตยกรรมที่คล้ายกันมาก

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.