2010-11-22 10 views
27
class TestClass 
{ 
    private string _privateString = "hello"; 
    void ChangeData() 
    { 
     TestClass otherTestClass = new TestClass(); 
     otherTestClass._privateString = "world"; 
    } 
} 

यह कोड सी # और PHP में समकक्ष कार्यों में संकलित करता है, लेकिन क्या कोई कारण बता सकता है कि otherTestClass._privateString क्यों बदला जा सकता है?कक्षा के उदाहरण से निजी सदस्य चर क्यों बदला जा सकता है?

मैंने सोचा होगा कि किसी वर्ग के एक उदाहरण को किसी भी परिस्थिति में एक निजी सदस्य चर बदलने में सक्षम नहीं होना चाहिए, और otherTestClass._privateString तक पहुंचने का प्रयास करने से 'सुरक्षा स्तर के कारण पहुंच योग्य' त्रुटि मिल जाएगी।

यह है मामला नहीं है, हालांकि, तो क्यों आप निजी सदस्यों तक पहुंचने देने के अपने ही वर्ग के अंदर एक वस्तु instantiating करता है? और यह चाहिए, यह एक हद तक इस ब्रेक encapsulation नहीं है? या क्या मुझे कुछ याद आ रही है?

  • (मैं पूछ रहा हूँ नहीं करता है, तो ऊपर वर्ग डिजाइन अच्छा अभ्यास है, बस इसे पीछे सिद्धांत के बारे में सोच।)

संपादित - जवाब और टिप्पणियों के लिए धन्यवाद। स्पष्टीकरण के लिए, मुझे यह जानने में भी दिलचस्पी है कि ऐसा करने में सक्षम होने के नाते सकारात्मक सुविधा के रूप में माना जाता है, या यदि यह बेहतर संकलन-समय की जांच/कोड स्पष्टता के लिए एक आवश्यक व्यापारिक है/क्योंकि अधिकांश अन्य भाषाएं इस तरह या जो कुछ भी करती हैं। ऐसा लगता है कि आदर्श रूप से संकलक आपको इसके बारे में चेतावनी देगा या चेतावनी देगा, लेकिन फिर मैं एक भाषा डिजाइनर से बहुत दूर हूं। इस तरह से होने के तरीके के बारे में कोई भी उदाहरण आपको कुछ उपयोगी करने देता है (बिना encapsulation का उल्लंघन किए) जो अन्यथा मुश्किल या असंभव होगा।

+0

बीटीडब्लू: आप 'चेंजडाटा() '' स्थिर' भी बना सकते हैं और आप अभी भी निजी सदस्यों तक पहुंच पाएंगे। – ulrichb

+0

@ulrichb - ओपी के लिए नोट करना महत्वपूर्ण है कि आप 'चेंजडाटा() '' स्थिर' होने पर निजी सदस्यों तक पहुंचने के लिए 'इस' कीवर्ड का उपयोग नहीं कर सकते हैं। – TheCloudlessSky

+1

रूबी में अलग-अलग भाषा का एक उदाहरण के रूप में, सार्वजनिक समान है, लेकिन निजी साधन "केवल उसी उदाहरण से सुलभ" हैं और संरक्षित साधन "केवल उसी वर्ग से पहुंच योग्य" हैं। विरासत में इसके साथ कुछ लेना देना नहीं है। – Tesserex

उत्तर

35

निजी सदस्य उस वर्ग के प्रोग्राम टेक्स्ट (नेस्टेड प्रकारों सहित) के भीतर किसी भी कोड तक पहुंच योग्य हैं। उस वर्ग के उदाहरण के साथ इसका कोई लेना-देना नहीं है जिसके साथ आप काम कर रहे हैं। एपीआई अभी भी कार्यान्वयन से अलग है, लेकिन कार्यान्वयन "जानता" खुद के बारे में जो उदाहरण इसे देख रहा है की परवाह किए बिना -

मैं इस कैप्सूलीकरण का उल्लंघन करती है विश्वास नहीं है।

मुझे विश्वास है कि कुछ अन्य भाषाओं में यह नहीं है कि कैसे पहुंच योग्यता काम करती है, लेकिन यह निश्चित रूप से सी # और जावा के लिए है। (जावा के पास निजी सदस्यों तक पहुंचने के बारे में थोड़ा अलग नियम हैं, लेकिन आपके द्वारा लिखे गए अनुवाद के लिए अनुवादित कोड अभी भी काम करेगा।)

+3

उदाहरण स्तर पर पहुंच को लागू करने के लिए प्रत्येक सदस्य चर पहुंच के लिए रन-टाइम चेक की आवश्यकता होगी, जबकि इस मॉडल को संकलित समय पर चेक किया जा सकता है। –

+1

@ जेम्स: ठीक है, जरूरी नहीं।आप * आवश्यकता हो सकती है कि निजी सदस्य केवल "इस" संदर्भ के माध्यम से उपलब्ध थे। यह घृणित, लेकिन संभव होगा। –

+1

मैं जॉन के जवाब में जोड़ूंगा कि इस प्रकार के अभिगम नियंत्रण में एन-एरी ऑपरेटरों को समानता जैसे आसानी से लिखा जा सकता है। समानता ऑपरेटर को लागू करना अधिक कठिन होगा यदि न तो किसी अन्य उदाहरण के लिए अन्य निजी सदस्यों तक पहुंच हो। –

9

ऐसा इसलिए है क्योंकि सी # कक्षा-स्तर की गोपनीयता को लागू करता है और ऑब्जेक्ट-स्तरीय गोपनीयता नहीं।

अधिकांश मुख्यधारा की भाषाएं समान नीति लागू करती हैं, यानी सी #, सी ++ और जावा। मुझे लगता है कि कारण हैं:

1) क्योंकि डेवलपर इस तरह की नीति के आदी हैं;

2) क्योंकि बहुत कम फायदे के बदले ऑब्जेक्ट-स्तरीय गोपनीयता बहुत कठिन हो जाएगी।

+0

मुझे विश्वास नहीं है कि वहां "इस" का उपयोग करने की आवश्यकता हो, क्योंकि कंपाइलर सदस्य चर को अलग करने में सक्षम हैं। मुझे लगता है कि उदाहरण के लिए प्रत्येक वर्ग के सदस्य मूल्य के लिए गेटर विधियों की आवश्यकता होगी। वास्तव में, यह encapsulation के खिलाफ होगा क्योंकि आप अन्य सदस्यों को निजी सदस्यों को भी उजागर करेंगे! – Simone

+0

@ miket2e ऑब्जेक्ट-स्तरीय गोपनीयता के साथ एक कॉपी कन्स्ट्रक्टर या सरल समान कार्य को कार्यान्वित करने का प्रयास करें। वर्तमान सी # में यह आसान है: इसे वापस करें ._somePrivateField.Eq uals (other._somePrivateField) - यदि आप अन्य ._somePrivateField तक पहुंच सकते हैं, तो आप सार्वजनिक गेटर्स को जोड़ने के बिना ऐसी सुविधा कैसे कार्यान्वित करेंगे? –

+1

@ माइकलस्टम: फ़ील्ड होने का एक फायदा उदाहरण-निजी या उदाहरण-संरक्षित है कि ऐसा करने से यह स्पष्ट हो जाता है कि व्युत्पन्न कक्षाएं उन क्षेत्रों को फिर से उद्देश्य दे सकती हैं जो बिना लिस्कोव प्रतिस्थापन सिद्धांत का उल्लंघन किए। अन्यथा, इस तरह के पुन: उद्देश्य से एलएसपी उल्लंघन हो सकता है। 'इक्वाल्स' जैसी कुछ को क्लास-प्राइवेट 'इक्वाल्स' विधि के द्वारा कार्यान्वित किया जा सकता है जो अन्य ऑब्जेक्ट की सामग्री को स्वीकार करता है (या तो असतत पैरामीटर का समूह, या क्लास-संरक्षित प्रकार का उपयोग करके), और जनता के बराबर 'ऑब्जेक्ट की विधि' राज्य 'को अपने राज्य को' संरक्षित 'के बराबर विधि के बराबर करती है। – supercat

संबंधित मुद्दे

 संबंधित मुद्दे