Objective c 如何在NSObject中实现保留计数? 我的问题是,当前版本的基础(或者ObjytoC运行时库,因为这似乎在那里)如何实现对 NSbObjs派生对象的保留计数?正如我在上所看到的,在NSObject的接口主体中没有名为retaincount的ivar。相反,似乎有一种表或映射包含每个对象的引用计数器。但是如果retain count真的是用map来完成的,那么使用这种实现,retain和release操作不是太昂贵了吗(因为,在这种情况下,有必要锁定和解锁互斥对象,所以除了在多线程环境中一次只能保留/释放一个对象之外,还需要查找映射以找到正确的对象)

Objective c 如何在NSObject中实现保留计数? 我的问题是,当前版本的基础(或者ObjytoC运行时库,因为这似乎在那里)如何实现对 NSbObjs派生对象的保留计数?正如我在上所看到的,在NSObject的接口主体中没有名为retaincount的ivar。相反,似乎有一种表或映射包含每个对象的引用计数器。但是如果retain count真的是用map来完成的,那么使用这种实现,retain和release操作不是太昂贵了吗(因为,在这种情况下,有必要锁定和解锁互斥对象,所以除了在多线程环境中一次只能保留/释放一个对象之外,还需要查找映射以找到正确的对象),objective-c,cocoa,nsobject,objective-c-runtime,retaincount,Objective C,Cocoa,Nsobject,Objective C Runtime,Retaincount,我在\u objc\u rootAllocWithZoneat(似乎是由[NSObject alloc]调用的函数)和\u class\u createInstanceFromZoneat(稍后由\u objc\u rootAllocWithZone调用)中都没有找到任何与分配新对象时将retain计数器设置为1相关的内容.NSObject的保留计数确实保存在全局映射中。IIRC实际上使用了一组映射,这些映射可能基于对象的地址进行分区,以减少锁争用,但实际的实现细节只是实现细节 在任何情况下,您

我在
\u objc\u rootAllocWithZone
at(似乎是由
[NSObject alloc]
调用的函数)和
\u class\u createInstanceFromZone
at(稍后由
\u objc\u rootAllocWithZone
调用)中都没有找到任何与分配新对象时将retain计数器设置为1相关的内容.

NSObject的保留计数确实保存在全局映射中。IIRC实际上使用了一组映射,这些映射可能基于对象的地址进行分区,以减少锁争用,但实际的实现细节只是实现细节


在任何情况下,您都找不到将保留计数设置为1的代码,因为没有任何代码。保留计数为1的对象不会被放入映射中。只有当对象
retain
ed超过初始值1时,才会进入保留计数映射。这是一种优化,可加快从不具有保留计数ri的对象的常见情况se超过1。

…对于标记指针的特殊情况,这些指针根本没有保留计数。数据本身在指针中进行编码,因此从技术上讲,您可以通过值而不是引用来传递它们(因为引用就是值,引用后面没有任何实际内容)。是的。当然,任何重写
-retain
-release
的类都可以自由地拥有自己的保留计数实现。有许多类确实将保留计数嵌入到ivar中,因为它们更喜欢加速
retain
release
,代价是拥有一个更大的对象。好的。B但是为什么他们不使用ivar作为计数器,这样可以降低保留/释放的成本?你知道使用maps是否有任何特殊原因吗?@luisantonibotelhoo.Leite:这将使系统上每个对象的大小增加4-8字节(取决于体系结构)。这可能会导致整个对象类增加一个malloc bucket大小(例如16到32字节)。还有很多对象的保留计数永远不会超过1,这会导致这些对象不必要地浪费空间。我相信您可以放心,
retain
release
也经过了大量优化,您不必担心性能问题。在我工作的所有岁月中对于Obj-C,我想不起来曾经看到过
retain
release
在时间配置文件上制造了足够多的光点来保证对它进行第一次思考。-(nsuiger)retainCount{return rand()};哦,天哪,我把终止放错地方了;…今晚我不会睡觉。