1

Instruments shows a memory leak from simply opening and closing the alert controller.

@IBAction func delBtnAc(sender: AnyObject) {

    let deleteAlert = UIAlertController(title: "Delete Image?", message: "", preferredStyle: .Alert)

    let cancelIt = UIAlertAction(title: "Cancel", style: .Cancel, handler: nil)

    deleteAlert.addAction(cancelIt)
    presentViewController(deleteAlert, animated: true, completion: nil)
}

I have reduced the alert to only a cancel button for testing.

Edited: Removed deleteAlert.dismissViewController in closure. Fixed retain cycle, but still shows a memory leak. Perhaps a bug.

agent86
  • 105
  • 12

2 Answers2

5

Your alert action's completion handler has a strong reference to your alert controller.

Your alert action has a strong reference to its completion handler.

Your alert controller has a strong reference to the alert action.

So here we have a classic retain cycle.

The problem is the strong reference from the completion handler to the alert controller itself, which in this case, happens to be completely unnecessary. The alert controller dismisses itself after running the appropriate completion handler.

We can completely eliminate the line.

If we were doing something non-redundant in the completion handler, we would need to create a weak reference to the completion handler so that we could use that in the completion handler.

nhgrif
  • 61,578
  • 25
  • 134
  • 173
  • 1
    Replacing action with let cancelIt = UIAlertAction(title: "Cancel", style: .Cancel, handler: nil). I still have the leak. – agent86 Aug 09 '15 at 18:45
  • If you're still seeing the leak without the retain cycle, then it could be a bug with Alert Controller. Or it could be a bug with Instruments even (Instruments certainly has bugs). Either way, it might be worth posting a bug report to Apple if you're certain that you don't have a retain cycle. – nhgrif Aug 09 '15 at 20:54
  • Still shows a leak, probably a bug. Thanks for your help. – agent86 Aug 10 '15 at 19:39
  • 3
    In case anyone has this problem in 2016. I still have a leak after set handler = nil, like @agent86 had. I found out that setting "tintColor" of alertController before it was presented cause the problem (eg. deleteAlert.view.tintColor = xxx). Delete or move it to be after "presentViewController" solved the problem for me. This is very weird, but this is the only change I made. Don't know if setting other properties will cause the same problem or not. – Daron Tancharoen Nov 17 '16 at 11:11
0

I found the same problem.

I solved it by setting the alert to null after button action:

deleteAlert = null inside your cancel button action

Gustavo Baiocchi Costa
  • 1,379
  • 3
  • 16
  • 34