不知道为什么,但是做一个简单[[NSOpenPanel openPanel] runModal];
的操作会造成内存泄漏——在 Leaks Instrument 中可以看到。
好像没了
是自动释放的对象,不应该是ARpool耗尽后自动释放吗?
有没有办法解决这个问题?
不知道为什么,但是做一个简单[[NSOpenPanel openPanel] runModal];
的操作会造成内存泄漏——在 Leaks Instrument 中可以看到。
好像没了
是自动释放的对象,不应该是ARpool耗尽后自动释放吗?
有没有办法解决这个问题?
NSOpenPanel
是一个单例,这意味着您每次使用它时总是得到相同的对象实例。这意味着您第一次调用[NSOpenPanel openPanel]
时,会创建一个实例NSOpenPanel
而不是释放它。
这不是泄漏,而是优化。但是,有时 Leaks 工具会将此类仅一次实例化为泄漏,因为这些实例(根据设计)从未发布。
NSOpenPanel
是一个如此广泛使用和测试的类,其标准实现中的任何泄漏都不太可能存在。
NSOpenPanel 不是单例。它可能曾经是一次,但查看最新的 NSOpenPanel.h 文件可以清楚地表明它不是单例,或者至少 Apple 不希望您利用此实现细节。
至于泄漏,我对何时应该释放打开的面板并保留它感到困惑。从文件系统编程指南的使用打开和保存面板部分,您的生活在 10.7 及更高版本中变得更加轻松:
Important: In OS X 10.6 and earlier, you must retain an open panel prior to displaying it and release it when you are done with it. Because the openPanel method returns an autoreleased object, the panel is normally released shortly after it appears on screen. Retaining the panel prevents it from being deallocated and dismissed prematurely. You do not need to retain the panel if it is attached to a window and you do not need to retain the panel in OS X 10.7 and when using ARC.
一旦我停止保留它,事情就变得容易了,变得容易多了:)
Instruments 在检测泄漏方面并不完美 - 特别是对于自动释放的物体,并且有误报的趋势。您可以尝试创建一个新的 NSAutoreleasePool,然后在完成 NSOpenPanel 以强制提前释放时将其排空 - 但我怀疑您实际上并没有泄漏。如果您确信代码看起来不错并且是自动发布的,那么它可能没问题。
NSOpenPanel
在使用 10.12 SDK 和 Swift 3.0.1 在 OS X 10.11.6 上构建的非沙盒应用程序中使用时,我看到 Xcode 的内存图工具中报告了“泄漏” 。PlugInKit 类(PKHostPlugin、PKDiscoveryDriver 等)中报告了“泄漏”,即使唯一的代码行是let openPanel = NSOpenPanel()
.
在沙盒环境中,打开面板由 powerbox 在单独的进程中绘制,而不是由 AppKit 本身绘制。当用户选择要打开的文件时,macOS 将该文件添加到应用程序的沙箱中。
在我对应用程序进行沙箱处理后,“泄漏”并没有出现在 Xcode 的内存图中,因为 NSOpenPanel 实现代码不再在应用程序的地址空间中,所以我不再需要担心它。