将Swift闭包对象添加到NSMutableArray然后将其删除不起作用 - LEAK

时间:2017-09-14 08:58:35

标签: ios swift memory-leaks closures nsmutablearray

我有一些与Objective C互操作的Swift代码,我注意到我正在泄漏,我把它缩小到NSMutableArray而不是删除我的闭包,这里是一个纯粹的Swift片段来重现这个问题:

let myClosure  : ((String?) -> ())! = { (fileName: String?) in
}

let arr = NSMutableArray()
arr.add(myClosure) 
arr.remove(myClosure)

有没有人遇到过这种情况 - 为什么会发生这种情况?我怎样才能让它发挥作用?

2 个答案:

答案 0 :(得分:1)

闭包没有引用,因此数组无法比较删除闭包对象,这就是为什么它不会从数组中删除。

您的代码

let arr1 = NSMutableArray()
arr1.add(myClosure)     
print(arr1)          //("(Function)")
arr1.remove(myClosure) 
print(arr1)          //("(Function)")

<强>解决方案

var arr = Array<Any>()
arr.append(myClosure)
print(arr)          //[(Function)]
arr.remove(at: 0)
print(arr)          //[]

这将通过索引删除所以你必须使用索引来删除元素而不是关闭实例我也建议你在Swift中使用纯swift类。

答案 1 :(得分:-1)

再次强调,我们的代码库使用与ObjC交互的Swift,因此,在我的情况下,不可能简单地使用纯Swift。

我更改了我们的API以使用从NSUInteger句柄映射到闭包的NSDictionary,然后使用该整数从字典中删除闭包。

该API的目的是注册侦听器回调并具有取消注册它们的功能。这样NSUInteger句柄就能满足删除位。