के साथ उद्देश्य सी मेमोरी प्रबंधन अब मैं कुछ समय के लिए ब्लॉक का उपयोग कर रहा हूं, लेकिन मुझे लगता है कि एआरसी और गैर-एआरसी वातावरण दोनों में स्मृति प्रबंधन के बारे में मुझे कुछ याद आती है। मुझे लगता है कि गहरी समझ से मुझे कई मेमोरी लीक कम हो जाएंगी।ब्लॉक, एआरसी और गैर-एआरसी
AFNetworking किसी विशेष एप्लिकेशन में ब्लॉक का मेरा मुख्य उपयोग है। अधिकांश समय, एक ऑपरेशन के पूरा होने वाले हैंडलर के अंदर, मैं कुछ ऐसा करता हूं जैसे "[self.myArray addObject]"।
एआरसी और गैर-एआरसी सक्षम वातावरण दोनों में, "स्वयं" this article from Apple के अनुसार बनाए रखा जाएगा।
इसका मतलब है कि जब भी एक एएफनेटवर्किंग नेटवर्क ऑपरेशन के समापन ब्लॉक को बुलाया जाता है, तो उस ब्लॉक के अंदर स्वयं को बनाए रखा जाता है, और उस ब्लॉक को दायरे से बाहर कर दिया जाता है। मेरा मानना है कि यह एआरसी और गैर-एआरसी दोनों पर लागू होता है। मैंने लीक्स टूल और स्टेटिक विश्लेषक दोनों को भाग लिया है ताकि मुझे कोई मेमोरी लीक मिल सके। कोई भी कोई नहीं दिखाया।
हालांकि, हाल ही में यह तब तक नहीं था जब तक मैंने एक चेतावनी पर ठोकर खाई जिसे मैं समझ नहीं पाया। मैं इस विशेष उदाहरण में एआरसी का उपयोग कर रहा हूं।
मैं दो उदाहरण चर कि पूरा होने और एक नेटवर्क आपरेशन
@property (nonatomic, readwrite, copy) SFCompletionBlock completionBlock;
@property (nonatomic, readwrite, copy) SFFailureBlock failureBlock;
@synthesize failureBlock = _failureBlock;
@synthesize operation = _operation;
कोड में कहीं की विफलता का संकेत है, मैं यह कर:
[self.operation setCompletionBlockWithSuccess:^(AFHTTPRequestOperation *operation, id
responseObject) {
NSError *error = [NSError errorWithDomain:@"com.test" code:100 userInfo:@{@"description": @"zero results"}];
_failureBlock(error);
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {
NSLog(@"nothing");
}];
Xcode लाइन है कि कॉल के बारे में शिकायत विफलता ब्लॉक, इस ब्लॉक में दृढ़ता से "कैप्चरिंग" स्वयं संदेश के साथ एक सतत चक्र में परिणाम होने की संभावना है। मेरा मानना है कि एक्सकोड सही है: विफलता ब्लॉक स्वयं को बरकरार रखता है, और स्वयं ब्लॉक की अपनी प्रति रखता है, इसलिए दो में से कोई भी नहीं हटा दिया जाएगा
हालांकि, मेरे पास निम्नलिखित प्रश्न/टिप्पणियां हैं।
1) यदि मैं _failureBlock (त्रुटि) को "self.failureBlock (त्रुटि)" (उद्धरण के बिना) में बदलता हूं तो संकलक शिकायत करना बंद कर देता है। ऐसा क्यों है? क्या यह एक स्मृति रिसाव संकलक याद आती है?
2) आम तौर पर ब्लॉक का उपयोग करते समय एआरसी और गैर-एआरसी सक्षम वातावरण दोनों में ब्लॉक के साथ काम करने का सबसे अच्छा अभ्यास क्या है जो उदाहरण चर हैं? ऐसा लगता है कि AFNetworking में पूर्णता और विफलता ब्लॉक के मामले में, वे दो ब्लॉक उदाहरण चर नहीं हैं, इसलिए संभवतः वे ऊपर वर्णित चक्रों को बनाए रखने वाले चक्रों की श्रेणी में नहीं आते हैं। लेकिन AFNetworking में प्रगति ब्लॉक का उपयोग करते समय, ऊपर दिए गए चक्रों को बनाए रखने से बचने के लिए क्या किया जा सकता है?
मुझे एआरसी और गैर-एआरसी पर अन्य लोगों के विचारों को स्मृति प्रबंधन के साथ ब्लॉक और मुद्दों/समाधान के साथ सुनना अच्छा लगेगा। मुझे इन परिस्थितियों में त्रुटि-प्रवण लगता है और मुझे लगता है कि चीजों को साफ़ करने के लिए इस पर कुछ चर्चा आवश्यक है।
मुझे नहीं पता कि यह महत्वपूर्ण है, लेकिन मैं नवीनतम एलएलवीएम के साथ एक्सकोड 4.4 का उपयोग करता हूं।
इस उत्तर के लिए धन्यवाद। यह विचार के लिए बहुत खाना है। एक तरफ ध्यान दें, आपने कॉलबैक के बारे में क्या कहा और क्रैश के कारण पृष्ठभूमि थ्रेड सही है। हालांकि, ऐसी समस्याओं से बचने के लिए, मेरे मामले में मुख्य धागे में सभी समापन ब्लॉक को बुलाया जाता है।अन्य चीजों के लिए, चक्र को बनाए रखने के लिए "एक विधि से ब्लॉक को वापस करें" समाधान, जो एक पुन: प्रयोज्य घटक बनाने की मूल समस्या को हल नहीं करता है जहां कॉलर पूर्णता ब्लॉक का निर्णय लेगा। – csotiriou
यदि आप ब्लॉक कॉलबैक के साथ एक एपीआई उजागर कर रहे हैं, तो आप अपने कॉलर्स को अपने स्वयं के बनाए रखने वाले चक्र बनाने से नहीं रोक सकते हैं। आपके एपीआई को कॉलबैक ब्लॉक को जल्द से जल्द जारी करने के लिए सावधानी बरतनी चाहिए, और शायद एक रद्द विधि का पर्दाफाश करना चाहिए जो कॉलबैक ब्लॉक भी जारी करेगा। व्यावहारिक रूप से, अधिकतर कॉलर कॉलबैक इनलाइन को लागू करेंगे, वैसे भी गुणों में नहीं। उस स्थिति में, स्मृति सेमेन्टिक्स एक विधि से ब्लॉक को वापस करने के समान होते हैं - बनाए रखने के चक्र तब शुरू होते हैं जब वे आपके एपीआई को कॉल करते हैं और समाप्त होते हैं जब आपका एपीआई कॉलबैक ब्लॉक जारी करता है। –