2012-07-11 11 views
7

मैं मेरी कक्षा में एक सरल विधि है:उद्देश्य-सी ब्लॉक अभी भी ढेर में कॉपी किए बिना क्यों काम करता है?

- (void)getFormWithBlock:(DataCenterResultBlock)block { 
    [SomeClass doSomeLongOperationWithParam:someParam 
            completionBlock:^(NSData *data, NSURLResponse *response) { 
             //Success 
             block(aVar, YES); 
            } errorBlock:^(NSError *error) { 
             //Failed 
             block(nil, NO); 
            }]; 
} 

मैंने पढ़ा है कि आप ढेर करने के लिए ब्लॉक कॉपी चाहिए अगर आप कुछ कर रहे हैं अतुल्यकालिक रूप से, क्योंकि वे ढेर पर आवंटित किए जाते हैं और एक बार कॉल पेड़ rewinds यह चला जाएगा ।

लेकिन यहां, मैं इसे ढेर में कॉपी नहीं कर रहा हूं लेकिन फिर भी मुझे कोई क्रैश नहीं मिलता है। क्यूं कर? धन्यवाद

+1

क्या आप एआरसी का उपयोग कर रहे हैं? – RolandasR

+0

हां मैं एआरसी – 0xSina

उत्तर

9

Block variables are copied to the heap automatically by ARC compilers:

7,5। ब्लाकों

... retainable वस्तु मालिक प्रकार के

__block चर ढेर प्रतिलिपि से चलती का परिणाम के साथ ढेर प्रति आरंभ से ढेर बंद ले जाया जाता है।

संपादित मुझे लगता है कि मैं सवाल गलत समझा: आप ब्लॉक के बारे में पूछा वस्तुओं खुद को, चर ब्लॉक नहीं। इस मामले में जवाब थोड़ा अलग है, लेकिन यह इसके लिए उबलता है: एआरसी स्वचालित रूप से सही चीज करता है।

एआरसी जानता है कि वर्तमान स्कोप रिटर्न के बाद उपयोग किए जाने पर ब्लॉक लिटरल की प्रतिलिपि बनाई जानी चाहिए। गैर-एआरसी कोड स्पष्ट रूप से कॉपी करने के लिए की जरूरत है और autorelease ब्लॉकों दिखाई:

return [[^{ 
    DoSomethingMagical(); 
} copy] autorelease]; 
एआरसी के साथ

, यह बस हो जाता है:

return ^{ DoSomethingMagical(); }; 

(here से)

+0

का उपयोग कर रहा हूं बस इस उत्तर को पढ़ने वाले अन्य लोगों के लाभ के लिए, उत्तर वास्तव में यहां प्रश्न से मेल नहीं खाता है (संभवतया सिर्फ गलत पढ़ा गया है)। सवाल एक स्टैक आवंटित ब्लॉक को किसी अन्य विधि में पास करने के बारे में है। उत्तर ब्लॉक में __block चर को कैप्चर करने का संदर्भ देता है। वे दो अलग-अलग मुद्दे हैं। –

+0

@FirozeLafeer आप बिल्कुल सही हैं, मैंने सवाल को गलत तरीके से पढ़ा। मैंने इसे इस बार वास्तविक प्रश्न का उत्तर देने के लिए संपादित किया :) धन्यवाद! – dasblinkenlight

1

[SomeClass doSomeLongOperationWithParam:completionBlock:errorBlock:] चाहिए पूर्णता और त्रुटि ब्लॉक की प्रतिलिपि बनाओ।

आपको लगता है कि विधि के क्रियान्वयन को देखें, तो यह शायद सही काम करने और ब्लॉक है कि आप। एआरसी या कोई एआरसी में पारित कर दिया, कि विधि उन ब्लॉकों कॉपी चाहिए को कॉपी कर रहा है।

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