runtime的优化
clean memory
- 是指加载后不会发生改变的内存
class_ro_t是属于 clean memory,是只读的
clean memory 可以进行移除从而节省更多的空间

dirty memory
- 是指在程序运行时会发生更改的内容
- 类结构一经使用就会变成
dirty memory, 因为运行时会向他写入新的数据
dirty memory比clean memory更耗性能
- 只要进程在运行,他就必须存在
dirty memory 被分为两部分,一部分为clean memory


成员变量和属性以及编码

- 对OC文件用
Clang进行编码为C++查看底层的实现
xcrun -sdk iphonesimulator clang -arch arm64 -rewrite-objc main.m -o main-arm64.cpp

NSObject_IVRS 是 isa, 也是成员变量的首地址
- 可以看出
属性生成了下划线_成员变量,属性都被注释掉了

编码

例如: @16@0:8 -> 表示
@ -> id ,返回值
16 -> 占用的内存
@ -> 参数 id, 0 -> 从0号位置开始
: -> SEL,, 8 -> 从8号位置开始
setter方法的底层原理
- 当我们赋值
copy修饰的name是person.name = leevi,回调用setName 方法
setName 又会调用底层的objc_setProperty, 根据C++的代码我也可以看出
- 将
setName 的 sel 定位到 imgp(objc_setProperty)
- 而用
strong 修饰的 则采用的内存平移赋值

什么时候定位到objc_setProperty
- 是在编译时,所以我们要通过
llvm的源码来查看内部的流程




- 可以看出使用
copy修饰的话,会走objc_setProperty
- 默认都是
strong 修饰


- 底层调用的是
reallySetProperty
- 普通的赋值都是对
新值的retain, 旧值的releaae
attomic 修饰时,加了一个 PeropertyLocks的自旋锁,所以读写比较慢
类方法的存储

+类方法存在元类的class_rw_t里
- 其实
类方法就是元类的实例方法
类方法存储的ABI方式解析
void wlwObjc_copyMethodList(Class pClass){
unsigned int count = 0;
Method *methods = class_copyMethodList(pClass, &count);
for (unsigned int i=0; i < count; i++) {
Method const method = methods[i];
NSString *key = NSStringFromSelector(method_getName(method));
NSLog(@"Method, name: %@", key);
}
free(methods);
}
void wlwInstanceMethod_classToMetaclass(Class pClass){
const char *className = class_getName(pClass);
Class metaClass = objc_getMetaClass(className);
Method method1 = class_getInstanceMethod(pClass, @selector(sayHello));
Method method2 = class_getInstanceMethod(metaClass, @selector(sayHello));
Method method3 = class_getInstanceMethod(pClass, @selector(sayHappy));
Method method4 = class_getInstanceMethod(metaClass, @selector(sayHappy));
NSLog(@"%s - %p-%p-%p-%p",__func__,method1,method2,method3,method4);
}
void logClassMethod_classToMetaclass(Class pClass){
const char *className = class_getName(pClass);
Class metaClass = objc_getMetaClass(className);
Method method1 = class_getClassMethod(pClass, @selector(sayHello));
Method method2 = class_getClassMethod(metaClass, @selector(sayHello));
Method method3 = class_getClassMethod(pClass, @selector(sayHappy));
Method method4 = class_getClassMethod(metaClass, @selector(sayHappy));
NSLog(@"%s-%p-%p-%p-%p",__func__,method1,method2,method3,method4);
}
void logIMP_classToMetaclass(Class pClass){
const char *className = class_getName(pClass);
Class metaClass = objc_getMetaClass(className);
IMP imp1 = class_getMethodImplementation(pClass, @selector(sayHello));
IMP imp2 = class_getMethodImplementation(metaClass, @selector(sayHello));
IMP imp3 = class_getMethodImplementation(pClass, @selector(sayHappy));
IMP imp4 = class_getMethodImplementation(metaClass, @selector(sayHappy));
NSLog(@"%p-%p-%p-%p",imp1,imp2,imp3,imp4);
NSLog(@"%s",__func__);
}