• iOS对象模型学习


    更新记录

    时间 更新记录
    2020年4月6日 初稿

    前言

    • iOS的对象模型,在《Objective-C基础教程》第2版 4.3-继承的工作机制中,用了一两页的篇幅来说明,而且很简单,易于理解。
    • 而笔者特地写下这一篇文章,是因为这个知识点,是OC开发的基础。所谓基础不牢,地动山摇。先把最基础的知识点学透,总结好,再逐渐地一点点刨深入的细节。
    • 不同于之前写的C++对象模型学习,这里不会有若干种对象模型的对比。直接拍出当前Objective-C的对象模型。

    iOS对象模型

    对象内存布局

    • OC中的对象都继承于NSObject,它们和C++对象类似,实例变量(C++里就叫成员变量)都存在于对象的内存之中。
    • 由于OC中没有虚函数的概念,所以并没有所谓的“虚函数指针”
    • 基类到子类的实例变量依次排列。由于OC对象都继承于NSObject,所以对象的第0个偏移量对应的就是isa指针。
    • 举《Objective-C基础教程》第2版 4.3-继承的工作机制中的例子,继承链为:RoundedRectangle---->Shape----->NSObject。RoundedRectangle对象的内存模型如图:

    方法调度机制

    • 众所周知,在OC调用一个对象的方法(C++就叫成员函数罗),其实就是给这个对象发消息(objc_msgSend
    • 对象的方法列表存储在【isa指针指向的类对象】中
    • 类的类方法列表(C++里面就叫静态成员函数)存储在元类(元类就是类对象的isa指针指向的对象)对象中
    • 举《Objective-C基础教程》第2版 4.3-继承的工作机制中的例子,生成的对象的方法列表:

    对象、类对象、元类对象的关系

    • 这里主要是参考iOS底层原理总结 - 探寻OC对象的本质,盗一张图,简洁果断地说明三者的关系

    • 和C++的比较

      • 优点
        • 增加了灵活性和便捷性
      • 缺点
        • 调用方法(C++里面叫成员函数)比C++慢的多,因为需要遍历方法列表,查找到相应的方法实现。
        • 不如C++安全。因为C++的编译器和连接器可以确保对象能够处理对应的方法。而Obejctive-C中,如果被发送消息的对象不能处理该消息,就会得到运行时错误。(unrecognized selector sent运行时错误,写过一段时间OC代码的同行应该都遇到过)

    参考资料

  • 相关阅读:
    #4702. gcd
    独特的树叶

    搞笑的代码 ( funny )
    越野赛车问题
    删边(cip)
    最长公共子序列
    美食节
    线段树
    新年快乐
  • 原文地址:https://www.cnblogs.com/HelloGreen/p/12643659.html
Copyright © 2020-2023  润新知