• Effective Objective-C 2.0 — 第14条:理解“类对象“的用意


    • 每个实例都有一个指向Class 对象的指针,用以表明其类型,而这些 Class 对象则构成了类的继承体系。
    • 如果对象类型无法在编译期确定,那么就应该使用类型信息查询方法来探知。
    • 尽量使用类型信息查询方法来确定对象类型,而不要直接比较类对象,因为某些对象可能实现了消息转发功能。

    类型 id 能指代任意的Objective-C 对象类型,编译器假定 类型为 id 的对象 能响应所有消息

    Objective-C 对象的本质

    每个 Objective-C 对象实例都是指向某块内存数据的指针。,所以在声明变量时,类型后面要跟一个”*“字符

    NSString *pointerVariable = @"Some string";

    id 本身已经是 指针了

    id genericTypedString = @"Some string";
    描述Objective-C 对象所用的数据结构定义在运行期程序库的头文件里,
    typedef struct objc_object [
         Class isa;
    } *id;

    typedef struct objc_class *Class;
    struct objc_class {
         Class isa;
         Class  super_class;
         const char *name;
         long version;
         long info;
         long instance_size;
         struct objc_ivar_list *ivars;
         struct objc_method_list **methodLists;
         struct objc_cache *cache;
         struct objc_protocol_list *protocols;
    };

    此结构体存放类的“元数据”(metadata)。
    类对象所属的类型,即isa指针所指向的类型,叫做“元类”(metaclass)。
    用来表述类对象本身所具备的元数据。


    “isMemberOfClass:”能够判断出对象是否为某个特定类的实例。
    “isKindOfClass:”能够判断对象是否为某类或其派生类的实例。

    比较类对象是否等同。一般用 == 操作符,而不用“isEqual:”。
    因为类对象是“单例”,在应用程序范围内,每个类的class仅有一个实例。

    但是最好还是使用类型信息查询方法。而不应该直接比较两个类对象是否等同。
    因为牵着可以正确处理那些使用了消息传递机制的对象。比方说:
    某个对象可能会把其收到的所有选择子都转发给另一个对象。
    这样的对象叫做“代理”(proxy),此种对象均以NSProxy为根类。
    通常情况下,在此种代理对象上调用class方法,那么返回的是代理对象本身。而非接受的代理的对象所属的类。
    若是使用类型信息查询方法,那么代理对象就会把这条消息转给“接受代理的对象”。
  • 相关阅读:
    集合之Map和List线程安全问题
    vue直接赋值后数据不更新
    使用sysmon事件映射ATT&CK
    blackhat议题"通过RPC防火墙拦截横向渗透"
    大数据Hadoop之——新一代流式数据湖平台 Apache Hudi
    【云原生】MySQL on k8s 环境部署
    【云原生】Presto/Trino on k8s 环境部署
    【云原生】Flink on k8s 讲解与实战操作
    【云原生】Spark on k8s 讲解与实战操作
    【云原生】Elasticsearch + Kibana on k8s 讲解与实战操作
  • 原文地址:https://www.cnblogs.com/IDRI/p/5181296.html
Copyright © 2020-2023  润新知