以编程方式确定从 nib/xib 加载的 Cocoa 对象是否可用

发布于 2024-09-11 19:50:50 字数 600 浏览 3 评论 0原文

设置如下:

  • 我在 nib 文件中有一个 cocoa 对象,该对象在加载 NSWindow 和视图时加载
  • 窗口可以关闭
  • 我也以编程方式访问该对象

现在在某些情况下会发生崩溃,当我尝试向该对象发送消息,但它之前已被释放(因为窗口已关闭)。崩溃看起来像这样:

Exception Type:  EXC_BAD_ACCESS (SIGSEGV) 
Exception Codes: KERN_INVALID_ADDRESS at 0x0000000000000017 
Crashed Thread:  0  
Dispatch queue: com.apple.main-thread

Application Specific Information: 
objc_msgSend() selector name: ...

有什么方法可以检查对象是否可用?检查 nil 不起作用,它不是 nil。也许控制流并不完美,我可以重写应用程序的其他部分来解决这个问题,但我认为这是一个更普遍的问题,我没有解决方案,它可以归结为:

如何确保从 nib 加载的对象在释放时设置为 nil?

The setting is the following:

  • I have a cocoa object in a nib file that is loaded when the NSWindow and view is loaded
  • The window can be closed
  • I also access the object programmatically

Now what happens in some situations is that I get a crash, when I try to send a message to the object, but it has been deallocated before (because the window is closed). The crash looks like this:

Exception Type:  EXC_BAD_ACCESS (SIGSEGV) 
Exception Codes: KERN_INVALID_ADDRESS at 0x0000000000000017 
Crashed Thread:  0  
Dispatch queue: com.apple.main-thread

Application Specific Information: 
objc_msgSend() selector name: ...

Is there any way to check if the object is available or not? Checking for nil does not work, it is not nil. Probably the control flow is not perfect, and I could rewrite other chunks of the app to make this problem go away, but I think this is a more general problem that I have no solution for, and it boils down to this:

How can I make sure that an object that is loaded from a nib is set to nil on deallocation?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

烟柳画桥 2024-09-18 19:50:50

我想你可以使用 Interfacebuilder 来编写你的 Window 类,并在它的 dealloc 方法中你可以将 VARIABLE 设置为 nil。但你不能将对象本身设置为零。该变量保存一个指向对象的指针,如果它被释放,则该指针指向内存中可能存在任何东西的位置。

因此,如果您从另一个类访问该对象,则会有另一个变量,因此将 Windows 类中的变量设置为 nil 根本没有用。

解决方案非常简单,因为当窗口被释放时,窗口类会向该对象发送一条释放消息,因此您应该在另一个类中使用该对象之前保留该对象,然后在使用完该对象后释放它。

如果您使用带有保留属性的对象属性,请不要忘记使用 self 调用 setter。object = ... 没有属性,它可能看起来像这样:

所以您需要保留您的对象在窗口关闭之前。也许在您的应用程序调用的第一个 viewDidLoad 方法中:


...
- (void)viewDidLoad {
otherClassObject.YOUROBJECT = [self.YOUROBJECT retain];

I guess you could use Interfacebuilder to write your Window-class and in its dealloc method you could set the VARIABLE to nil. But you cannot set the object itself to nil. the variable saves a pointer to the object, if its deallocated the pointer points to a place in memory where anything could be.

So if you access said object from another class, you have another variable, so setting the one in your windows-class to nil, wouldnt be useful at all.

The solution is quiet simple, since the window-class sends this object a release message when the window get deallocated, you should retain your object bevor you use it in another class, and then release it when youre done with it.

If you use a property for your object with the retain-attribute dont forget to call the setter with self.object = ... without property it could look sth like this:

so you need to retain your object bevor the window gets closed. maybe in the first viewDidLoad-method that gets called by your app:


...
- (void)viewDidLoad {
otherClassObject.YOUROBJECT = [self.YOUROBJECT retain];

夜还是长夜 2024-09-18 19:50:50

尝试在 Interface Builder 上停用窗口设置“关闭时释放”。

Try deactivating the window setting "Release when close" on Interface Builder.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文