Prevent ARC from deallocating something that's not currently being used but will be soon?

automatic-ref-counting, ios, objective-c

Solution

If an object were to remain in memory, and you do not have a reference to it, this is known as a memory leak. As I said in my comments, you need to keep some kind of reference to it so that a) it is not deallocated, b) you can send a message to it, and c) you can deallocate it before your class is deallocated.

The most obvious way to do this would be with a property in your class. Since you said that you don't want to do that (maybe you have a lot of them) then another possible solution would be to keep an array of cached objects that you plan on reusing and eventually deallocating.

Problem

I've run into this problem a couple of times and want to know the correct approach to take. For an example, let's say I'm writing an iPhone app and I want a custom alert view class that uses blocks. So I write the class, then later on in my code I go: ``` MyAlertView *alert = [MyAlertView alertWithBlahBlahBlah...]; [alert addButton:@"button" withBlock:^{ ... }]; [alert show]; ``` Somewhere in the alert view class, we have ``` - (void)addButton:(NSString *)button withBlock:(void (^))block { [_blocks setObject:[block copy] forKey:button]; } - (void)show { ... drawing stuff ... UIButton *button = ... [button addTarget:self selector:@selector(buttonPressed:) ...]; ... } - (void)buttonPressed:(id)sender { ((void (^)())[_blocks objectForKey:[sender title]])(); } ``` So, the alert view now shows up just fine. The problem is, if I tap a button, it attempts to send the `buttonPressed:` selector to the `MyAlertView` object that was displayed. The `MyAlertView` has, however, been removed from the superview at this time. ARC decides that because the alert view is not owned by anyone anymore, it should be deallocated, not knowing that a button needs to message it in the future. This causes a crash when the button is tapped. What's the right way to keep the alert view in memory? I could make the `MyAlertView` object a property of the class that's using it, but that's kind of silly (what if I want to show two alerts at once?).

Original source