Obj-c运行时:找到另一个类属于哪个类

时间:2014-02-07 16:52:30

标签: iphone objective-c macos objective-c-runtime

假设我有这个:

@interface ThingManager : NSObject
@property Thing *aThing;
@end

aThing是否有办法在运行时知道它是ThingManager的属性?

3 个答案:

答案 0 :(得分:1)

除非你告诉它,否则它就是。

您可以将ThingManager弱属性添加到Thing并在ThingManager中实现setter,如下所示:

- (void)setAThing:(Thing *)thing {
    if (_aThing != thing) {
        _aThing = thing;
        _aThing.manager = self;   // this is the relevant line
    }
}

答案 1 :(得分:1)

除非你有aThing属性的自定义setter,它在Thing对象上设置一些内容以告诉它它是什么。您可以让aThing setter方法设置一个属性,添加到Thing,告诉它管理员是谁。

答案 2 :(得分:1)

您从问题开始:

  

aThing是否有办法在运行时知道它是ThingManager的属性?

虽然目前为止答案尚未完全清楚,但您希望aThing能够确定ThingManger实例是否正在管理它。

所以在这一点上我们知道ThingManger类知道Thing类,你现在看起来想要反过来 - 你问Thing可以找到它{{1} }}?

但是当有人回答你发表评论时

  

所以ThingManagerThing需要彼此了解吗?嗯......松耦合不好。

嗯......如果你不想让ThingManager知道ThingThingManager如何问ThingManager是什么?

每个人对你的问题的解释是错误的吗?

也许你不关心松耦合但是关于强参考周期?如果这两个人彼此了解并在这样做的过程中创造了一个强大的循环,那么他们就有可能在你的申请需要之后很长时间内保持彼此活着 - 这是关注吗?

但是@DrummerB解决了这个问题 - 您使用Thing上的弱属性来引用其管理ThingManager。所以看起来强大的参考周期也不是你的关注......

然后你发表评论:

  

有没有办法看到谁在运行时引用了一个对象?

如上所述,这是一个非常不同的问题。对此的简短回答是没有[*]。

您是否可以编写一个Thing可以调用的方法来查找正在管理它的ThingManager,而Thing个实例和{{{{}}之间没有任何引用1}}实例?

如果是这样,这是一个大纲算法:

  1. ThingManager类保留所有create 和alive 实例的集合。活着的要求要求这个集合是某种弱集合(设计自己的集合或搜索弱集合)。
  2. ThingManager添加方法,找到ThingManager的经理,例如像Thing
  3. 之类的东西
  4. + (ThingManager *) managerFor:(Thing *)thing个实例在需要了解其经理时致电Thing
  5. 当然,这并不能解决你对疏松耦合的担忧 - 两个班级仍然必须知道彼此的存在......

    这使您回到让[ThingManager managerFor:self]具有Thing属性的直接解决方案。如果你想减少耦合,你可以将这个属性键入manager,所以它的任何旧对象,或id所以它的任何旧对象提供它实现你定义的一些最小的管理方法协议id<SomeMinimalManagerProtocol>

    看看SomeMinimalManagerProtocolNSWindow - 他们知道彼此。

    HTH


    [*]答案很长,(Objective-)C(++)并不是为了确保找到所有引用而设计的。这就是你听到诸如“保守的垃圾收集”这样的短语的原因。只有Objective-C对象有一个垃圾收集器,它由运行时的内部更改支持,但现在已弃用,并且应用程序无法轻松访问其机制以应用于其他用途。