alloc init和new的区别
2020-08-20 本文已影响0人
一个半吊子工程师
本篇文章采用的源码是objc4-781版本
创建对象的两种方式:
UIView *myView = [[UIView alloc] init];
UIView *myView = [UIView new];
在Source/NSObject.mm文件中可以找到alloc方法和new方法的实现
+ (id)new {
return [callAlloc(self, false/*checkNil*/) init];
}
alloc init
通过new
方法创建的实例会调用init
方法,那么[Class alloc] init]
和[Class new]
这两种方法的唯一区别就在于分配内存这一步,我们可以先找到_objc_rootAlloc
的实现函数
上图中callAlloc
这个函数也是new
方法里面调用的函数。
区别:
new 方法调用的时候只传了2个参数,
_objc_rootAlloc 这里传了3个参
下面是callAlloc
的源码
从上面的源码来看alloc
和new
进来这个函数的差别什么呢?
就是allocWithZone
参数了,从alloc
那里的时候为true
,
new
进来的时候为默认值false
;
从整个callAlloc
用到allocWihZone
参数的地方就在于最后几行。
// No shortcuts available.
if (allocWithZone) {
return ((id(*)(id, SEL, struct _NSZone *))objc_msgSend)(cls, @selector(allocWithZone:), nil);
}
如果allocWithZone
为真则会走[cls allocWithZone:nil]
,反之则走[cls alloc]
[Class new]
就相当于调用[[Class alloc] init]
,一个为隐式调用,一个为显示调用而已。可以理解为 new
为一个快捷键
区别
1.alloc在分配内存的时候使用了zone, 它是在给对象分配内存的时候把关联的对象分配到一个相邻的区域内, 以便于调用时消耗很少的内存, 提升程序的处理速度;
2.使用new来创建对象的话, 初始化方法被固定死了, 只能使用init, 不能调用其他的initWith方法;
3.使用alloc init方法, 我们可以重写init方法, 但是如果使用new来创建的话就只能走系统的init方法了.