Objective-C 소기(3)클래스 2.0

2300 단어
대상(objc_object 구조체)과 마찬가지로 클래스(objc_class 구조체)는 새로운 운행 시에도 큰 변화가 생겼고objc-runtime-new.h에서 그 정의를 찾을 수 있다.
struct objc_class : objc_object {
    // Class ISA;
    Class superclass;
    cache_t cache;             // formerly cache pointer and vtable
    class_data_bits_t bits;    // class_rw_t * plus custom rr/alloc flags
    
    class_rw_t *data() { 
        return bits.data();
    }
    
    //  
};

C++로 바뀐 후objc_class 구조체가 objc_object 구조체에서 직접 계승되어 isa의 존재를 주석한 것을 알 수 있다.이전의 정의를 비교해 보면 두 번째 멤버는 여전히 부류를 가리키는 지침이었지만 그 후에는 완전히 달라졌다. cache의 유형이 cache_t로 바뀌었고 나머지 정보는 bits에 끼워 넣었다.bits의 오른쪽에서 호의적인 개발자가 후세에 남긴 주석을 볼 수 있는데 이 멤버도 isa와 유사하게 비트(bit)를 다른 용도로 사용했다고 설명했다.그 중에서 가장 중요한 것은 class_rw_t *인데 data() 함수는 이 구조체 바늘을 되돌려 주는 데 사용되고 class_rw_t의 이름은 클래스가 읽을 수 있고 쓸 수 있는 데이터임을 나타낸다.
계속해서 objc-runtime-new.h에서 class_rw_t 구조체의 정의를 보았다
struct class_rw_t {
    uint32_t flags;
    uint32_t version;

    const class_ro_t *ro;

    method_array_t methods;
    property_array_t properties;
    protocol_array_t protocols;

    Class firstSubclass;
    Class nextSiblingClass;

    char *demangledName;
}

이것은 클래스의 데이터만 읽는 구성원ro이 있다는 것을 알 수 있다. 이것은 클래스가 컴파일할 때 확정된 것이다. 클래스의 정의는 다음과 같다.
struct class_ro_t {
    uint32_t flags;
    uint32_t instanceStart;
    uint32_t instanceSize;
#ifdef __LP64__
    uint32_t reserved;
#endif

    const uint8_t * ivarLayout;
    
    const char * name;
    method_list_t * baseMethodList;
    protocol_list_t * baseProtocols;
    const ivar_list_t * ivars;

    const uint8_t * weakIvarLayout;
    property_list_t *baseProperties;

    method_list_t *baseMethods() const {
        return baseMethodList;
    }
};

실현 중class_rw_t구조체methods,propertiesprotocols는 구조체ro에 대응하는 데이터와category의 데이터를 포함하는데 이것은 실행할 때 하는 일이며 다음 글은 상세한 설명이 있을 것이다.이렇게 하면 메시지 발송에서 방법을 찾을 때 ro에서 검색할 필요가 없다.

총결산


클래스가 Objective-C가 실행될 때의 실현을 대체적으로 이해했고 구체적인 세부 부분도 서로 다른 기능을 분석할 때 구체적으로 분석해야 한다.

좋은 웹페이지 즐겨찾기