2011-01-16 22 views
8

कोड स्निपेट में, मैं वर्ग स्कोप के बाहर निजी सदस्य चर का उपयोग करने में सक्षम हूं। हालांकि यह कभी नहीं किया जाना चाहिए, इस मामले में इसकी अनुमति क्यों है? संदर्भ के द्वारा एक लौटा निजी चर प्राप्त करने के लिए यह एक बुरा अभ्यास है?जब मैं सार्वजनिक सदस्य समारोह से संदर्भ वापस करता हूं तो मैं निजी सदस्यों का खुलासा क्यों कर सकता हूं?

#include <iostream> 
#include <cstdlib> 

class foo 
{ 
    int x; 
    public: 
     foo(int a):x(a){} 
     int methodOne() { return x; } 
     int& methodTwo() { return x; } 
}; 

int main() 
{ 
    foo obj(10); 
    int& x = obj.methodTwo(); 
    x = 20;    // With this statement, modifying the state of obj::x 

    std::cout << obj.methodOne(); 
    getchar(); 
    return 0; 
} 

और इस विधि के संबंध में, रिटर्न प्रकार क्या बताता है? और मुझे इस प्रकार का रिटर्न प्रकार कब होना चाहिए?

int& methodTwo() { return x; } 

पुनश्च: मैं माफी चाहता हूँ अगर विषय पंक्ति अस्पष्ट है। क्या कोई इसे यहां प्रासंगिक सामग्री में बदल सकता है। धन्यवाद।

उत्तर

15

private का मतलब यह नहीं है कि "यह स्मृति केवल सदस्य कार्यों द्वारा संशोधित की जा सकती है" - इसका मतलब है "इस चर को एक्सेस करने के प्रत्यक्ष प्रयासों के परिणामस्वरूप संकलन त्रुटि होगी"। जब आप ऑब्जेक्ट का संदर्भ प्रकट करते हैं, तो आपने ऑब्जेक्ट को प्रभावी ढंग से उजागर किया है।

क्या संदर्भ के द्वारा एक लौटा हुआ निजी चर प्राप्त करने का यह एक बुरा अभ्यास है?

नहीं, यह आप जो चाहते हैं उस पर निर्भर करता है। std::vector<t>::operator[] जैसी चीजें लागू करने में काफी मुश्किल होगी अगर वे गैर-const संदर्भ वापस नहीं कर सके :) यदि आप एक संदर्भ वापस करना चाहते हैं और नहीं चाहते हैं कि ग्राहक इसे संशोधित करने में सक्षम हों, तो बस इसे const संदर्भ बनाएं।

+0

द्वारा गुजरने वाले लोगों के लिए: [यह प्रश्न] (http://stackoverflow.com/questions/8005514/is-returning-references-of-member-variables-bad-pratice) सुझाव देता है कि यह आपके संदर्भ को वापस करने के लिए खतरनाक हो सकता है कक्षा के सदस्य – Arthur

+0

@ आर्थर: हाँ, जैसा कि मैंने कहा था, यह इस बात पर निर्भर करता है कि आप क्या करना चाहते हैं। यह 'std :: vector' के लिए ठीक काम करता है - लेकिन ऐसे कई मामले हैं जहां यह भी गलत काम है। –

3

संदर्भ के रूप में निजी सदस्यों को लौटाना पूरी तरह से मान्य है और प्रोग्रामर जो कक्षा लिखता है वह ध्यान से चुनने के लिए जिम्मेदार है कि इसे अनुमति दी जानी चाहिए। This link ऐसा उदाहरण देता है जब यह किया जा सकता है।

2

इस कोड:

int& methodTwo() { return x; } 

मतलब फ़ंक्शन कि एक पूर्णांक के लिए एक संदर्भ। किसी फ़ंक्शन के संदर्भ में मूल्य पारित करने की तरह, यदि methodTwo का वापसी मान बदल जाता है, तो methodTwo मान वापस लौटाता है। इस मामले में, कक्षा क्षेत्र x

आपके द्वारा लिखे गए कोड में, इसका मतलब है कि आप निजी चर x अपने दायरे (कक्षा वर्ग) से बचते हैं और बाहरी दुनिया में पारित हो जाते हैं। यह निश्चित रूप से एक बुरा व्यवहार (है, क्योंकि x तरीके कि वर्ग foo टूट सकता है में बदला जा सकता है, लेकिन यह निश्चित स्वीकार्य है।

याद रखें सार्वजनिक/निजी/सुरक्षित है संकलन-समय केवल। आपके आवेदन संकलित हो जाता है, निजी क्षेत्र सार्वजनिक क्षेत्रों के बगल में बैठते हैं और संशोधन के खिलाफ कोई सुरक्षा नहीं है। सी # और जावा जैसी प्रबंधित भाषाओं के लिए भी यह सच है।

आपको आम तौर पर संदर्भों को वापस करने से बचना चाहिए क्योंकि यह समझने में कठोर-कठिन बनाता है जब रचनाकार/विनाशक कॉल करें। हालांकि, एक संदर्भ लौटने से तेज़ी से हो सकता है। यदि आपकी विधि ने एक स्ट्रक्चर प्रकार लौटाया जो विशाल था, उसी स्ट्रैंड को कॉन्स्ट संदर्भ देता है uct प्रकार केवल चार-से-आठ-बाइट्स (उस ऑब्जेक्ट के लिए पॉइंटर) लेना चाहिए। हालांकि, इस तरह की चीज के लिए अनुकूलित करने के बेहतर तरीके हैं।

+1

मैं दृढ़ता से दृढ़ता से असहमत हूं कि "आपको संदर्भों को वापस करने से बचना चाहिए" बिंदु - यह देखते हुए कि संकलक प्रतिलिपि बनाने के लिए प्रतिलिपि बनाने के लिए स्वतंत्र है, अगर आप मूल्य से वापस आते हैं, तो केवल एक चीज जो आप कई मामलों में प्राप्त करते हैं मान धीमा डीबग बनाता है (क्योंकि संकलक रिलीज मोड में आपके ऊपर आरवीओ/एनआरवीओ करता है)। –

+1

गुरु-स्तर सी ++ उपयोगकर्ता नहीं होने के नाते, मुझे गलत होने का अधिकार सुरक्षित है :) लेकिन यदि आप किसी स्थानीय चर के संदर्भ को वापस करते हैं तो क्या आपको अपरिभाषित व्यवहार नहीं मिलेगा? (यानी, आपको स्टैक पर कुछ यादृच्छिक स्थान पर पॉइंटर के साथ छोड़ा गया है?) –

+0

यह सही है। अपरिभाषित व्यवहार में संदर्भ परिणामों के माध्यम से एक नष्ट चर का उपयोग करने का प्रयास। लेकिन संदर्भ के द्वारा लौटने वाले वर्ग गेटर्स जैसी चीजों के लिए सामान्य और अपेक्षित व्यवहार है। –

0

डोनोतोलो की तरह, यह पूरी तरह से मान्य है।निजी सदस्यों का विचार अन्य कक्षाओं/कार्यों को के निजी सदस्य तक पहुंचने के लिए आपकी अनुमति के बिना अनुमति देना है। आप अन्य वर्गों/कार्य अपने निजी सदस्यों का उपयोग करने की अनुमति देने के लिए एक समारोह बनाने के लिए खुश हैं, तो संकलक वास्तव में :-)

आमतौर पर उस के खिलाफ कुछ भी नहीं है, यह एक निजी सदस्य है और एक पाने के लिए उपयोगी है समारोह के मूल्य प्राप्त करने के लिए अन्य वर्गों/कार्यों को अनुमति देने के लिए फ़ंक्शन, लेकिन केवल कक्षा इसे बदलने में सक्षम होगी।

-1

मैं तुम्हें main() में x की बात कर रहे हैं वर्ग गुंजाइश

बाहर निजी सदस्य चर का उपयोग करने में सक्षम हूँ तो उस xclass foo में घोषित से अलग है। यदि आप obj.x तक पहुंचने का प्रयास करते हैं तो संकलक निश्चित रूप से शिकायत करेगा।

क्या संदर्भ के द्वारा एक लौटा हुआ निजी चर प्राप्त करने का यह एक बुरा अभ्यास है?

किसी निजी सदस्य के संदर्भ में "प्राप्त करने" में कुछ भी गलत नहीं है। लेकिन एक निजी सदस्य के संदर्भ को देने से यह निजी बेकार घोषित करता है। एक वैरिएबल घोषित करने के लिए एक निजी सदस्य होने के लिए आप उस सदस्य तक पहुंच केवल वर्ग के तरीकों तक सीमित कर सकते हैं।

इस विधि के संबंध में, रिटर्न प्रकार क्या बताता है? और मुझे इस प्रकार का रिटर्न प्रकार कब होना चाहिए?

यह सुनिश्चित नहीं है कि आप किस विधि का जिक्र कर रहे हैं?!?!?

+2

वास्तव में? यह बेकार बनाता है? आप 'std :: vector :: ऑपरेटर [] 'तब कैसे समझाते हैं? जो भी बफर पॉइंटर वेक्टर उपयोग कर रहा है वह दुनिया के सामने नहीं है, लेकिन डेटा (और होना चाहिए, वेक्टर के बिंदु को दिया जाना चाहिए) –

+0

@ बिली ओ'नेल: अच्छा बिंदु। इस पर ध्यान दिलाने के लिए धन्यवाद। – yasouser

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

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