更新:
func identity<T>(_ v: T) -> T { return v } var closure = { return } while true { closure() closure = identity(closure) }
原版的:
原标题:Swift:闭包数组导致EXC_BAD_ACCESS代码= 2
我试图理解为什么这段代码产生EXC_BAD_ACCESS代码= 2.这是代码:
var closures: [() -> ()] = [] closures.append({ return }) while true { var newClosures: [() -> ()] = [] for closure in closures { closure() newClosures.append(closure) } closures = newClosures }
我试图将问题提炼到尽可能少的行,这就是为什么代码看起来有点奇怪和毫无意义. (它唯一的“观点”是用尽可能少的线来证明我所遇到的问题.)
如果您在XCode中将此代码作为macOS控制台应用程序运行,您将看到正在分配内存而不会被释放.在Instruments中我可以看到内存是在newClosures.append(closure)中分配的,这是有道理的.我不明白为什么为newClosures分配闭包不会释放旧版本的newClosures.相反,分配似乎无限增长,直到我EXC_BAD_ACCESS代码= 2.
值得注意的是,它甚至没有分配太多内存.在我的测试中,应用程序在分配大约17MB后崩溃(它从大约5MB开始,并在大约60s内上升到17MB).所以我认为它与保留的对象数量有关,而不是它们的纯粹大小.
如果我用一个数组将闭包数组替换为其他引用类型,例如
class Foo { } var foos: [Foo] = [] foos.append(Foo()) while true { var newFoos: [Foo] = [] for foo in foos { newFoos.append(foo) } foos = newFoos }
它按预期工作.我认为必须在闭包每次循环中捕获越来越多的东西时会发生什么?但我不明白这是怎么回事.
解决方法
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。