代码之家  ›  专栏  ›  技术社区  ›  Jared Pochtar

objective-c中的对象是否在不经过alloc的情况下创建?

  •  1
  • Jared Pochtar  · 技术社区  · 15 年前

    我知道objective-c运行时中有一些函数允许您直接创建对象,比如类createinstance。我想知道的是,除了根类(nsobject)alloc方法之外,是否有其他函数实际使用了这些函数。我认为像kvc绑定这样的东西可能存在,但iphone操作系统上没有这些(据我所知,如果我错了,请纠正我),那么有什么可以做到这一点的吗?

    如果您想知道/这很重要,我希望通过在类上声明没有ivar,而是重写+alloc方法并调用类_createInstance(self,numberOfBytesofMyVars)来绕过objc运行时来分配实例的大小。

    谢谢

    编辑 我想我需要更具体一些。我将在运行时向运行时添加类,并可能卸载和重新加载同一类的更改版本。到目前为止,由于类addmethod之类的原因,我已经解决了大部分问题,但是在类注册之后,没有对应的ivar。我能想到的两个解决方案是在运行时没有实际的ivar,但是重写alloc以确保通过extrabytes为它们留出足够的空间,或者声明一个ivar,它是指向所有实际ivar的指针,然后我可以很明显地做任何事情想要的。我更喜欢使用前一种策略,但是有很多事情可能会出错,比如如果有东西分配了我的对象的一个实例,而没有经过我的重载alloc方法。有人知道其中一件事吗?

    4 回复  |  直到 15 年前
        1
  •  1
  •   Ken    15 年前

    我不确定你是想改变现有类的行为,这是不安全的,还是想为你拥有的自定义类做点什么,这些类是nsobject的直接子类,很可能是。

    在实践中看到的几乎所有nsstring都是私有子类的实例,该子类为与对象内联的字符串分配空间。例如,字符数据不是包含指向char*的指针,而是紧跟在对象中的ivar之后。中的extrabytes参数 NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone) 有这样的用途吗?

    所以一方面,是的,你可以像那样耍花招。另一方面,你需要知道你在做什么 你的 东西。如果您尝试使用nsstring的私有子类(它是私有的,所以您只需要通过运行时内省与之交互)执行类似的操作,则可能会发生冲突。

    有一些公共cocoa类也可以做这样的事情,所以如果您的类直接继承自nsobject,那么您就最好了。nslock就是其中之一。nslock的自定义子类的内存布局如下 { isa, <ivars of NSLock> <ivars of subclass of NSLock> <more NSLock stuff, space reserved using the extraBytes parameter> } .

    另外,请注意,+alloc calls+allocWithZone:,+allocWithZone:是更常见的重写点。

        2
  •  0
  •   Community CDub    8 年前

    我不知道你为什么要按照你的建议去做--我看不出你有什么理由 不能 做吧,但是根据 this post ,通常没有理由使用 class_createInstance 直接(我不知道有什么特别的用法)。 类创建实例 也不考虑内存区域或 alloc . 如果你只是想隐瞒你的隐私 better ways .

    编辑: 我想你在找 class_addIvar 函数,它(顾名思义)动态地向类添加ivar。它只适用于新的运行时,所以它不会在模拟器上工作,但它会在iphone上工作。

    编辑2: 只是想说清楚(万一还没说清楚),你完全可以依赖 allocWithZone 总是有人打电话来。基本可可类,如 NSString NSArray 重写 异硫腙 . 类创建实例 几乎从未使用过,除非在运行时级别使用,所以您不必担心cocoa的任何部分在类中使用它。所以最初的问题的答案是“否”(或者更具体地说,对象有时是在没有 同种异体 ,但不是没有 异硫腙 ,至少据我所知)。

        3
  •  -1
  •   JeremyP    15 年前

    从技术上来说,没有什么可以阻止你超越alloc。只需在类中创建一个名为+alloc的方法。我只是想不出你为什么要这么做。

        4
  •  -1
  •   ExitToShell    15 年前

    听起来你太难管理内存了。让操作系统在创建对象时动态分配内存。如果你使用过多,操作系统会发送一个通知,告诉你已经接近极限了。在那一点上你可以释放你不再需要的东西。

    如果你需要太多的内存以至于不得不使用技巧,那么你的实现可能需要在核心层重新考虑,而不是试图将你的方形设计融入iphone操作系统的圆孔中。

    只是我的意见基于你提供的信息。

    推荐文章