एक ही नाम के साथ कई कक्षाएं, लेकिन विभिन्न नामस्थान?


11

मैं कुछ कोड (C # अगर यह मायने रखता है) में चला गया है जिसमें कक्षाएं हैं जिनका समान नाम है, लेकिन उनके नामस्थानों में भिन्न हैं। वे सभी एक ही तार्किक चीज़ का प्रतिनिधित्व करते हैं, लेकिन अक्सर एक ही वस्तु के अलग-अलग "विचार" होते हैं। विभिन्न नाम स्थान एक ही समाधान के कई बार होते हैं, और यहां तक ​​कि एक ही dll भी।

मेरे पास अपने विचार हैं, लेकिन इस अभ्यास के बारे में कुछ भी निश्चित नहीं पाया जा सका है कि उपलब्ध साधनों का एक चतुर उपयोग या बचने के लिए एक पैटर्न माना जाए।

स्मर्फिंग नामकरण पर यह सवाल इस पर है, लेकिन दूसरी दिशा से। नामों की अवहेलना करने के लिए संभावित रूप से एक मनमाना और व्यापक उपसर्ग की आवश्यकता होगी, जिसे वह प्रश्न समाप्त करना चाहता था।

इस अभ्यास के आसपास क्या दिशानिर्देश हैं?


1
ओओपी में कई अपवाद हैं, लेकिन सबसे पहले मैं इस बुरे डिजाइन पर विचार करता हूं, खासकर अगर सभी वर्ग समान स्तर की पहुंच साझा करते हैं। जब मैं किसी भी फ़ाइल में एक क्लास का नाम पढ़ता हूं, तो मैं यह जानना चाहता हूं कि नेमस्पेस निर्देशों का उल्लेख किए बिना क्लास को तुरंत किस नामस्थान में रखा गया है।
लियोपोल्ड एस्परगर

कई संबंधित वस्तुओं के लिए एक वैध मामला है जो एक ही राज्य के साथ सौदा करते हैं, लेकिन आम तौर पर उन्हें फ़ंक्शन द्वारा अलग किया जाता है। हो सकता है कि आपके पास एक वस्तु हो जो एक दृश्य के लिए एक मॉडल को गोद ले। एक अन्य व्यक्ति वस्तु पर गणना कर सकता है। एक और एडेप्टर या मुखौटा हो सकता है। आप हो सकता है तो FooAdapter, FooViewer, FooCalculator, आदि लेकिन निश्चित रूप से एक ही बात का नाम नहीं। उन विशिष्ट वर्गों के बारे में अधिक जानकारी के बिना जिनके बारे में आप बात कर रहे हैं, हालांकि, उत्तर देना मुश्किल है।

@ जॉनघन - Employeeउदाहरण के रूप में विचार करें । एक कर्मचारी है जो अन्य कर्मचारियों के लिए है, एक एचआर के लिए है, एक बाहरी जोखिम के लिए है। वे सभी "कर्मचारी" नामित किए गए हैं और उन सभी के पास सहायकों (EmployeeRepository, EmployeeView, आदि) की किस्में हैं। वे सभी एक ही dll में हैं, और जब वे कुछ सामान्य गुण (नाम, शीर्षक) साझा करते हैं, तो वे सभी भिन्न होते हैं (फोन नंबर, वेतन)।
तेलस्टीन जूल

सिस्टम के साथ काम करने के बाद उस मॉडल Employeeरों कई बार, आप की तरह लगता है सभी विशेषताओं के मिलन के साथ एक मॉडल की जरूरत है और एक में शामिल हैं typeया departmentविशेषता। अन्यथा, कोड का अनावश्यक दोहराव है।

5
क्या नामस्थानों के शुरू होने का यह एक कारण नहीं था? नाम टकराव की अनुमति देने के लिए?
डैन पिचेलमैन

जवाबों:


5

मैं इस तरह के उपयोग के खिलाफ एक उत्तर देने की कोशिश करूँगा, जिसे देखने के बाद और मेरी एक परियोजना में भी इस पर काम किया है।

कोड पठनीयता

सबसे पहले, विचार करें कि कोड पठनीयता महत्वपूर्ण है और यह अभ्यास उसी के लिए काउंटर है। कोई व्यक्ति कोड का एक टुकड़ा पढ़ता है और चलो यह कहते हैं कि यह एक फ़ंक्शन है doSomething(Employee e)। यह अब पढ़ने योग्य नहीं है, क्योंकि Employeeविभिन्न पैकेजों में मौजूद 10 अलग-अलग वर्गों के कारण आपको यह जानने के लिए कि आपके इनपुट वास्तव में क्या हैं, यह जानने के लिए आपको सबसे पहले आयात घोषणा का सहारा लेना होगा।

यह, हालांकि, एक उच्च-स्तरीय दृश्य है और हमारे पास अक्सर यादृच्छिक नाम की झड़पें होती हैं, जिनके बारे में कोई परवाह नहीं करता है या यहां तक ​​कि पाता है, क्योंकि अर्थ शेष कोड से प्राप्त किया जा सकता है और आप किस पैकेज में हैं। इसलिए कोई भी बहस कर सकता है। स्थानीय स्तर पर, कोई समस्या नहीं है, क्योंकि यदि आप Employeeएक hrपैकेज के भीतर देखते हैं, तो आपको यह जानना होगा कि हम कर्मचारी के एचआर के बारे में बात कर रहे हैं।

जैसे ही आप इन पैकेजों को छोड़ते हैं, चीजें टूट जाती हैं। एक बार जब आप एक अलग मॉड्यूल / पैकेज / आदि में काम कर रहे हों और आपको किसी कर्मचारी के साथ काम करने की आवश्यकता हो, तो आप पहले से ही पठनीयता का त्याग कर रहे हैं यदि आप इसके प्रकार को पूरी तरह से योग्य नहीं करते हैं। इसके अतिरिक्त, 10 विभिन्न Employeeवर्गों के होने का अर्थ है कि आपकी IDE की स्वतः पूर्णता अब काम नहीं करेगी और आपको स्वयं को कर्मचारी के प्रकार से चुनना होगा।

कोड दोहराव

इनमें से प्रत्येक वर्ग की प्रकृति एक-दूसरे से संबंधित होने के कारण आपका कोड बहुत अधिक दोहराव के कारण बिगड़ने के लिए बाध्य है। ज्यादातर मामलों में, आपके पास एक कर्मचारी का नाम या कुछ पहचान संख्या जैसी कुछ होगी, जिसे प्रत्येक वर्ग को लागू करना होगा। भले ही प्रत्येक वर्ग अपने स्वयं के दृष्टिकोण को जोड़ता है, अगर वे अंतर्निहित कर्मचारी डेटा साझा नहीं करते हैं, तो आप बेकार के विशाल द्रव्यमान के साथ समाप्त हो जाएंगे, लेकिन महंगा, कोड।

कोड जटिलता

आप पूछ सकते हैं कि क्या इतना जटिल हो सकता है? आखिरकार, प्रत्येक वर्ग इसे जितना चाहे उतना सरल रख सकता है। वास्तव में एक समस्या यह बन जाती है कि आप परिवर्तनों को कैसे प्रचारित करते हैं। एक यथोचित सुविधा संपन्न सॉफ़्टवेयर में आप कर्मचारी डेटा को बदलने में सक्षम हो सकते हैं - और आप हर जगह इसे प्रतिबिंबित करना चाहते हैं। कहते हैं कि एक महिला ने सिर्फ शादी की और आपको उसका नाम बदलकर उससे अलग Xहोना पड़ाYउसके कारण। सभी जगह इस अधिकार को करने के लिए पर्याप्त है, लेकिन तब भी जब आप इन सभी अलग-अलग वर्गों के होते हैं। आपके अन्य डिजाइन विकल्पों के आधार पर, इसका मतलब यह आसानी से हो सकता है कि प्रत्येक वर्ग को अपने स्वयं के श्रोता को लागू करना होगा या इस तरह के बदलावों की सूचना देनी होगी - जो मूल रूप से एक ऐसे कारक के रूप में अनुवादित होता है जिसे उन कक्षाओं की संख्या पर लागू किया जाना है जिनसे आपको निपटना है। । और निश्चित रूप से अधिक कोड दोहराव, और कम कोड पठनीयता, .. इस तरह के कारक जटिलता विश्लेषण में अनभिज्ञ हो सकते हैं, लेकिन उन्हें यकीन है कि आपके कोड आधार के आकार पर लागू होने पर वे परेशान हैं।

कोड संचार

कोड जटिलता के साथ उपरोक्त समस्याओं के अलावा, जो डिज़ाइन विकल्पों से भी संबंधित हैं, आप अपनी उच्च-स्तरीय डिज़ाइन स्पष्टता को भी कम कर रहे हैं और डोमेन विशेषज्ञों के साथ ठीक से संवाद करने की क्षमता खो देते हैं। जब आप आर्किटेक्चर, डिज़ाइन या आवश्यकताओं पर चर्चा करते हैं, तो आप सरल कथन बनाने के लिए स्वतंत्र नहीं रह जाते हैं given an employee, you can do ...। एक डेवलपर को अब नहीं पता होगा employeeकि उस बिंदु पर वास्तव में क्या मतलब है। हालांकि एक डोमेन विशेषज्ञ इसे जरूर जानेंगे। हम सब करते हैं। की तरह। लेकिन सॉफ़्टवेयर के संदर्भ में अब संवाद करना इतना आसान नहीं है।

समस्या से कैसे छुटकारा पाएं

इससे अवगत होने के बाद और अगर आपकी टीम इससे सहमत है कि यह एक बड़ी समस्या है जिससे निपटने के लिए, तो आपको इससे निपटने के लिए एक तरीके से काम करना होगा। आमतौर पर, आप अपने प्रबंधक से पूरी टीम को एक सप्ताह का अवकाश देने के लिए नहीं कह सकते हैं ताकि वे कचरा बाहर निकाल सकें। तो संक्षेप में, आपको इन वर्गों को आंशिक रूप से समाप्त करने का एक तरीका खोजना होगा, एक समय में एक। इसके बारे में सबसे महत्वपूर्ण हिस्सा यह तय करना है - पूरी टीम के साथ - Employeeवास्तव में क्या है। सभी व्यक्तिगत विशेषताओं को एक ईश्वर-कर्मचारी में एकीकृत करें । एक कोर-कर्मचारी के बारे में अधिक सोचें और सबसे महत्वपूर्ण, यह तय करें कि वह Employeeवर्ग कहाँ निवास करेगा।

यदि आप कोड की समीक्षा करते हैं, तो यह सुनिश्चित करना विशेष रूप से आसान है कि समस्या कम से कम आगे न बढ़े, यानी जब वे Employeeफिर से एक और जोड़ना चाहते हैं तो सभी को अपने ट्रैक में रोक दें । यह भी ध्यान रखें कि नए सबसिस्टम सहमत का पालन करते Employeeहैं और पुराने संस्करणों तक पहुंचने की अनुमति नहीं है।

अपनी प्रोग्रामिंग भाषा के आधार पर, आप उन कक्षाओं को भी चिह्नित करना चाहते हैं, जिन्हें अंततः @Deprecatedआपकी टीम को तुरंत यह एहसास दिलाने में मदद करने के लिए कुछ के साथ समाप्त कर दिया जाएगा कि वे उस चीज़ के साथ काम कर रहे हैं जिसे बदलना होगा।

पुराने कर्मचारी वर्गों से छुटकारा पाने के लिए, आप प्रत्येक व्यक्तिगत मामले के लिए निर्णय ले सकते हैं कि यह कैसे सबसे अच्छा समाप्त हो जाता है, या बस एक सामान्य पैटर्न पर सहमत होता है। आप वर्ग के नाम को चिपका सकते हैं और इसे वास्तविक कर्मचारी के चारों ओर लपेट सकते हैं, आप पैटर्न (डेकोरेटर या एडेप्टर का ध्यान रखें), या, या का उपयोग कर सकते हैं।

एक लंबी कहानी को छोटा करने के लिए: यह "अभ्यास" तकनीकी रूप से ध्वनि है, लेकिन छिपी हुई लागतों से भरा है जो केवल सड़क के नीचे होगा। जबकि आप तुरंत समस्या से छुटकारा पाने में सक्षम नहीं हो सकते हैं, आप इसके हानिकारक प्रभावों से तुरंत शुरू कर सकते हैं।


एक कोर क्लास होने से एक अच्छा समाधान लगता है। अन्य वर्ग इससे बढ़ सकते हैं। आईडीई के बारे में, यह जानने के लिए कि कौन सा वर्ग आपको संदर्भ से सर्वोत्तम मिलान करने के लिए सुझाव देने के लिए पर्याप्त है, ऑटो समापन पर्याप्त स्मार्ट है। कुल मिलाकर, मैं यह नहीं देखता कि यह इतनी बड़ी समस्या क्यों है, खासकर अगर कोडबेस आंतरिक रूप से उपयोग किया जाता है।
सूचित

1
एक बार जब आप एक संदर्भ से बाहर हो जाते हैं, तो यह पर्याप्त स्मार्ट नहीं है। एक वर्ग पर विचार करें, जिसे वास्तव में समस्याग्रस्त दोनों वर्गों की आवश्यकता है - ऑटो-पूर्ण बिल्कुल मदद नहीं करेगा। और यह अन्य दस वर्गों से भी अलग नहीं होगा। लेकिन असली समस्या यह है कि टीम के नए सदस्य, जो यह भी नहीं जानते हैं कि उन सभी पैकेज डोमेन वास्तव में क्या हैं और उन्हें कौन सा चुनना चाहिए।
फ्रैंक

यदि एक ही नाम के कई वर्गों का एक ही संदर्भ में उपयोग किया जा रहा है, तो यह कठिन है। मैंने उस मामले को नहीं देखा है। मैंने कई वर्गों को एक ही नाम से देखा है, लेकिन वे अक्सर उसी संदर्भ में उपयोग नहीं किए जाते हैं जैसा आपने उल्लेख किया है।
सूचित किया गया

@randomA - दुख की बात है कि इस कोडबेस में यह मामला काफी सामान्य है।
तेलस्तीन

अच्छे अंक, लेकिन आपने वास्तव में मुख्य समस्या का हल नहीं दिया है, केवल एक ही समस्या है जब मूल समस्या हल हो जाती है ("एक कर्मचारी वास्तव में क्या है")। एकमात्र स्पष्ट "समाधान" ("एक ईश्वर-कर्मचारी में सभी व्यक्तिगत विशेषताओं को एकीकृत करें") आपने त्याग दिया, ठीक है। कहते हैं कि आपके पास DB.Employee, Marshalling.Employee, ViewModels.Employee, GUI.Views.Employee, आदि आपके समाधान क्या हैं?
पाब्लो एच

9

स्काला कलेक्शन फ्रेमवर्क इसका एक अच्छा उदाहरण है। उत्परिवर्तनीय और अपरिवर्तनीय संग्रह के साथ-साथ धारावाहिक और समानांतर (और शायद भविष्य में भी वितरित किए गए) संग्रह हैं। इसलिए, उदाहरण के लिए, चार Mapलक्षण हैं:

scala.collection.Map
scala.collection.immutable.Map
scala.collection.mutable.Map
scala.collection.concurrent.Map

प्लस थ्री ParMapएस:

scala.collecion.parallel.ParMap
scala.collecion.parallel.immutable.ParMap
scala.collecion.parallel.mutable.ParMap

और भी दिलचस्प:

scala.collection.immutable.Map            extends scala.collection.Map
scala.collection.mutable.Map              extends scala.collection.Map
scala.collection.concurrent.Map           extends scala.collection.mutable.Map

scala.collecion.parallel.ParMap           extends scala.collection.Map
scala.collecion.parallel.immutable.ParMap extends scala.collecion.parallel.ParMap
scala.collecion.parallel.mutable.ParMap   extends scala.collecion.parallel.ParMap

इसलिए, ParMapविस्तार ParMapकरता है Mapऔर Mapविस्तार Mapकरता है Map

और क्या: लेकिन, क्यों न हम स्वीकार करते हैं होगा आप उन्हें कहते हैं? यह सही समझ में आता है। यही नाम स्थान के लिए हैं!


3
"यही नामस्थान के लिए हैं!" => +1
svidgen

मुझे यह पसंद है, लेकिन C # /। NET की दुनिया में जब मैंने समानांतर कक्षाओं को एक समानांतर उप-नामस्थान में स्थानांतरित कर दिया, तब यह सहायक वर्ग System.Threading.Parallel के साथ टकराता है, जो मैं समानांतरता प्राप्त करने के लिए भारी उपयोग करता हूं। मैं इसके बजाय नामस्थान 'समवर्ती' का उपयोग नहीं करना चाहता था क्योंकि पहले से ही संग्रह कक्षाओं पर 'समवर्ती पहुंच' का उपयोग किया जा रहा है। एक समझौता के रूप में मैंने उप-नामस्थान 'समानांतर' का विकल्प चुना है।
Redcalx

2

यह एक वास्तविक दिलचस्प सवाल है जहां दो अनिवार्य रूप से विरोध करने वाले उत्तर दोनों सही हैं। यहाँ इस चर्चा का एक वास्तविक दुनिया उदाहरण है जो हम एक परियोजना पर कर रहे हैं।

मुझे लगता है कि अब तक दो बहुत ही प्रमुख विचार हैं जो आपको एक दिशा या दूसरे में जाना चाहते हैं, @ जोर्ग और @Frank से दो उत्तरों से आरेखण:

  1. यदि आप ऐसी स्थिति का अनुमान लगाते हैं, जिसमें समान-नाम वाली कक्षाओं में से एक से अधिक समान कोड संदर्भ में उपयोग किए जाने की आवश्यकता हो सकती है, तो यह एक ही नाम का उपयोग न करने का एक कारण है। यही है, अगर आप के साथ काम करने की जरूरत है, hr.Employeeलेकिन एक ही समय में अनुमति के माध्यम से देखने की जरूरत है security.Employee, यह कष्टप्रद वास्तविक तेजी से हो रहा है।
  2. इसके विपरीत, यदि आपकी कक्षाओं में समान नाम वाले सभी समान या बहुत समान एपीआई हैं, तो यह एक अच्छा उदाहरण है जब आपको अलग-अलग नामस्थानों के साथ एक ही नाम का उपयोग करना चाहिए । स्काला उदाहरण ठीक यही है, जहाँ सभी Mapवर्ग एक ही इंटरफ़ेस लागू करते हैं या एक दूसरे के उपवर्ग होते हैं। इस मामले में अस्पष्टता या "भ्रम" को यकीनन एक अच्छी बात कहा जा सकता है, क्योंकि उपयोगकर्ता कक्षा या इंटरफ़ेस के सभी कार्यान्वयनों को एक समान मान सकता है ... जो कि इंटरफेस और उपवर्गों का बिंदु है।
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.