2011-09-01 12 views

उत्तर

0

यह इवर (उदाहरण के चर) सुरक्षित रखने के लिए एक सम्मेलन है, इसलिए आप केवल गेटर और सेटर से पहुंच सकते हैं।

+2

डॉट सिंटैक्स का उपयोग न करने के लिए एक बेहतर सम्मेलन है। – jer

+4

@ सिंथेसाइज (और सामान्य रूप से गुण हैं) पूरी तरह से ऑर्थोगोनल डॉट सिंटैक्स के लिए। –

1

यहां कारण मैं कई बार ऐसा करते हैं:

अगर मैं एक संपत्ति मैं आम तौर पर मेरी इवर को रेखांकित करेंगे ताकि काम को बैक-एंड सर्वर से वांछित डेटा लोड करने के लिए किया पर आलसी लोड हो रहा है क्या करना चाहते हैं/बचाया फ़ाइल/क्या है-आप केवल पहली बार लोड किया गया है। उदाहरण के लिए:

- (NSMutableArray *)recentHistory; 
{ 
    if (_recentHistory == nil) 
    { 
     // Get it and set it, otherwise no work is needed... hooray! 
    } 

    return _recentHistory; 
} 

तो यहाँ संपत्ति [instanceOfClass recentHistory] (या instanceOfClass.recentHistory) करने के लिए कॉल इवर जाँच करेगा कि क्या यह डेटा लोड करने के लिए या सिर्फ पहले से ही भरी हुई डेटा वापस की जरूरत को देखने के लिए।

यह अपने सभी गुणों की इस तरह की घोषणा करने के overkill है।

उम्मीद है कि मदद करता है।

+2

लेकिन क्या आपको वास्तव में इसके लिए अंडरस्कोर का उपयोग करना है या क्या आपका मतलब सिर्फ एक सम्मेलन के रूप में है? आप 'हाल ही में इतिहास को' सिंथेसाइज कर सकते हैं; 'और' हालिया इतिहास 'विधि के अंदर आवृत्ति चर' हालिया इतिहास 'या' स्वयं-> हालिया इतिहास 'का उपयोग करें, बस सुनिश्चित करें कि संपत्ति का नाम' self.recentHistory' या '[self हालिया इतिहास] 'और एक रिकर्सन का कारण बनता है। एक सम्मेलन के रूप में –

+0

नहीं, नहीं। यह एक सम्मेलन है जिसे आप ऐप्पल के कोड में भी पाएंगे, जो लोग इसका उपयोग करते हैं। आईवर और संपत्ति रखने का विचार कभी-कभी अति प्रयोग किया जाता है, लेकिन यह एक ऐसा मामला है जहां मुझे लगता है कि यह तब से बना है। –

3

कभी कभी यह क्या दृश्यों को समझने के लिए पीछे हो रहा है देखने के लिए मदद करता है। मूल रूप से जब आप कार्यान्वयन में इस

@property (nonatomic, retain) Foo *foo; 
इस के साथ

देख

@synthesize foo=_foo; 

यह निम्नलिखित के लिए वाक्यविन्यास चीनी है, जिसका अर्थ है कि संकलक मूल रूप से के लिए आप

Foo *foo = nil; 

-(Foo *) foo { 
    return _foo; 
} 

-(void) setFoo:(Foo *)val { 
    if(_foo != val) { 
     [_foo release]; 
     _foo = [val retain]; 
    } 
} 

इस तरह इस कोड उत्पन्न करता है जब आप सार्वजनिक संपत्ति का संदर्भ लेते हैं, तो आप self.foo के जेनरेट किए गए सामानों के माध्यम से इसे दबाते हैं और यदि आप संदर्भित करना चाहते हैं आपके वर्ग के अंदर आवृत्ति चर आप _foo देख सकते हैं। एक्सकोड चार से पहले दोनों के बीच उलझन में आसान था। आप

self.foo = foo1; 

foo = foo2; 

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

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

+0

अच्छी व्याख्या। बस नाइटपिकिंग: 'अगर (_foo! = Nil) [_foo रिलीज़];' कंपाइलर टेस्ट बनाम शून्य उत्पन्न नहीं कर रहा है, जो बेकार होगा, यह जांच करेगा कि नया मान पिछले मान से अलग है या नहीं। उदाहरण के लिए http://stackoverflow.com/questions/3924463/how-is-retain-setter-implemented-with-synthesize/3925204#3925204 देखें। – jv42

+0

'Foo * tmp = [Foo foo] के साथ अपना कोड चलाने का प्रयास करें; self.foo = tmp; self.foo = tmp; 'यह देखने के लिए उछाल जाओ। – jv42

+0

मैंने अपने आईपैड पर उस जवाब को टक्कर लगी, मुझे सटीक कार्यान्वयन का 100% यकीन नहीं था, लेकिन मैं वास्तव में इस तथ्य को हाइलाइट करना चाहता था कि यह आपके लिए मेमोरी प्रबंधन को संभालता है और टकराव से बचने में मदद करता है। सर उठाने के लिए धन्यवाद! – jerrylroberts

1

बस सभी उपरोक्त उत्तरों में मेरे विचार जोड़ना चाहते थे।

मेरे मामले में, मैं इसका इस्तेमाल मुख्य रूप से मेरी कक्षाओं दुर्घटनाओं से सुरक्षित रखने के लिए।

मेरी ज फाइलों में, मैं कोई ivars के साथ ही गुण घोषणा करते हैं। .m फ़ाइल में, मैं उपरोक्त @synthesize पैटर्न का उपयोग अपने उपयोगकर्ताओं सहित वास्तविक आईवर को छिपाने के लिए करता हूं, ताकि संश्लेषित/गतिशील एक्सेसर्स का उपयोग करने के लिए मजबूर किया जा सके और अन्यथा इवर सीधे नहीं। आप अपने इवर नाम के लिए कुछ भी इस्तेमाल कर सकते हैं और न केवल इसे अंडरस्कोर कर सकते हैं। जैसेतुम कर सकते हो:

@synthesize foo = _mySecretFoo; 
@synthesize bar = oneUglyVarBecauseIHateMyBoss; 

इस तरह से, अपने मालिक केवल बार देखना होगा, और आप इसे, बहुत आसान है, और इस प्रकार सुरक्षित मिलेगा बार एक्सेसर उपयोग करने के लिए - चाहे आप डॉट नोटेशन या संदेशों का उपयोग करें।

मैं दूसरे के ऊपर इस दृष्टिकोण पसंद करते हैं,

@property (getter=foo, setter=setFoo, ...) _mySecretFoo; 
@property (getter=bar, setter=setBar, ...) oneUglyVarBecauseIHateMyBoss; 

इस निजी कार्यान्वयन और कैप्सूलीकरण लागू नहीं करता है के रूप में, और यह सिर्फ अतिरिक्त टाइपिंग जब Xcode आप के लिए भी ऐसा ही कर सकता है। याद रखने की एक बात, गुण इवर के समान नहीं हैं! आप इवर, या दूसरी तरफ से अधिक गुण हो सकता है।

+0

यदि मैंने यह अधिकार पढ़ लिया है, तो आप इसे '@ कार्यान्वयन {...} 'ब्लॉक में स्पष्ट रूप से ivars घोषित किए बिना करते हैं। '@ सिंथेसाइज बार = एकगुली' का उपयोग करने का क्या फायदा है; यदि आप कभी भी 'एकगुली' का उल्लेख नहीं करते हैं? क्यों न केवल '@ सिंथेसाइज बार' करें? क्या ऐसा इसलिए है क्योंकि यदि आप लिखते हैं तो आपका तरीका त्रुटियां देता है जैसे 'बार = 123.0'? –

+0

का मतलब है कि आप ivars को @interface {} ब्लॉक में घोषित करते हैं। हाँ यदि आप बार = 123 का उपयोग करते हैं तो आपको एक त्रुटि मिलेगी, लेकिन ऐसा नहीं है कि आप उपर्युक्त पैटर्न का उपयोग क्यों करेंगे। यह पैटर्न एक सुविधा है जो आपके कार्यान्वयन को पूरी तरह छिपाने के दौरान सार्वजनिक इंटरफ़ेस का पर्दाफाश करने की अनुमति देती है, जैसे कि सेब दस्तावेज़ों से इस उदाहरण की तरह: '@syntheize उम्र = संख्याऑफयर्स;' यह मुझे भी करने की अनुमति देता है: 'कुछ खाता * खाता = [कुछ खाता डिफ़ॉल्ट खाता ]; self.account = खाता; 'त्रुटियों के बारे में चिंता किए बिना, क्योंकि यह लेखन कोड की मेरी शैली है। यह पूरी तरह से सुविधा और कोडिंग शैली है। –

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