Writing in the front

As an iOS coder who has been writing business code for years, I have to create classes and objects, and ALLOc init is used very frequently. So what exactly do alloc and init do. With questions, let’s explore.

XHPerson *x0 = [XHPerson alloc];
XHPerson *x1 = [x0 init];
XHPerson *x2 = [x1 init];
NSLog(@"x0==%@--%p--%p", x0, x0, &x0);
NSLog(@"x1==%@--%p--%p", x1, x1, &x1);
NSLog(@"x2==%@--%p--%p", x2, x2, &x2);
Copy the code

What happens if you create three objects and print their contents, object addresses, and pointer addresses separately?

x0==<XHPerson: 0x1013a2770>--0x1013a2770--0x7ffeefbff468
x1==<XHPerson: 0x1013a2770>--0x1013a2770--0x7ffeefbff470
x2==<XHPerson: 0x1013a2770>--0x1013a2770--0x7ffeefbff460
Copy the code

As you can see, the contents and addresses of the three objects are the same, and the pointer addresses are different.

Conclusion: 1. Alloc has a memory pointer to it. 2. Init indicates the same memory and does not operate on the pointer. 3. Alloc opens memory, init does not open memory

Alloc source

So now that alloc is doing the memory thing, how does it do it? Init doesn’t do anything? What’s the point? Keep going down. Source code process:

1.alloc

+ (id)alloc {
    return _objc_rootAlloc(self);
}
Copy the code

2._objc_rootAlloc

id
_objc_rootAlloc(Class cls)
{
    return callAlloc(cls, false/*checkNil*/, true/*allocWithZone*/);
}
Copy the code

3.callAlloc

static ALWAYS_INLINE id callAlloc(Class cls, bool checkNil, Bool allocWithZone=false) {#if __OBJC2__ //objc2.0 // cls)) return nil; If (fastPath (!) {// If (fastPath (!); cls->ISA()->hasCustomAWZ())) { return _objc_rootAllocWithZone(cls, nil); } #endif // No shortcuts available. if (allocWithZone) { return ((id(*)(id, SEL, struct _NSZone *))objc_msgSend)(cls, @selector(allocWithZone:), nil); # } return ((id(*)(id, SEL))objc_msgSend)(cls, @selector(alloc)); }Copy the code

4._objc_rootAllocWithZone

id
_objc_rootAllocWithZone(Class cls, malloc_zone_t *zone __unused)
{
    // allocWithZone under __OBJC2__ ignores the zone parameter
    return _class_createInstanceFromZone(cls, 0, nil,
                                         OBJECT_CONSTRUCT_CALL_BADALLOC);
}
Copy the code

5._class_createInstanceFromZone (core instance creation method)

Three important things are done, which can be seen more clearly with screenshots

Object creation process

1. 'CLS ->instanceSize' calculates the memory size. 2. '(id)calloc(1, size)' opens memory. 3. 'obj->initInstanceIsa(CLS, hasCxxDtor)' associates the class with memory.Copy the code

InstanceSize method

FastInstanceSize method

Align16 method, 16-byte memory alignment

Caches free alignedInstanceSize method

Calloc method

Calloc opens up memory without executing the defined class

InitInstanceIsa method

Initialize ISA. The underlying mechanism of ISA is not analyzed.

The last

Alloc flowchart

conclusion

Through the analysis of alloc source code, it can be known that the main purpose of Alloc is to open up memory and associate ISA and CLS classes. There are three core steps to open up memory: calculate memory size, apply for memory space, and associate ISA and CLS classes