C and OC Call the [object Foo] method to differentiate:
In many languages, such as C, invoking a method is actually jumping to a point in memory and starting to execute a piece of code. There is no dynamic feature, because this is determined at compile time. In Objective-c, the [object Foo] syntax does not immediately execute the code of the Foo method. It is a message that sends an object called Foo at run time. This message, which may be handled by object, may be forwarded to another object, or it can be ignored to pretend that the message was confiscated. Many different messages can also be implemented with the same method. These are all determined when the program is running.
In fact, the syntax of the OBJECTIVE-C function call that you write at compile time will be translated into a function call of C-objc_msgsend (). For example, the following two lines of code are equivalent:
[Array Insertobject:foo atindex:5];
Objc_msgsend (Array, @selector (insertobject:atindex:), Foo, 5);
The key to messaging is hidden in the ISA pointer in Objc_object and the class dispatch table in Objc_class.
Objc_object, Objc_class and Ojbc_method
In Objective-c, classes, objects, and methods are all structures of C, and from the objc/objc.h header file, we can find their definitions:
struct Objc_object {
Class isa objc_isa_availability;
};
struct Objc_class {
class Isa objc_isa_availability;
#if!__objc2__
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;
#endif
};
struct Objc_method_list {
struct objc_method_list *obsolete;
int method_count;
#ifdef __lp64__
int space;
#endif/
* Variable length structure */
struct objc_method method_list[1];
};
struct Objc_method {
SEL method_name;
char *method_types; /* A String representing Argument/return types */
IMP method_imp;
};
The Objc_method_list essence is an array of variable lengths with Objc_method elements. A objc_method struct has a function name, the SEL, a string representing the type of the function (see Type Encoding), and the implementation of the function imp (IMP is the abbreviation for implementation, which is actually a function pointer to the first address of the method implementation )
From these definitions, you can see that sending a message also objc_msgsend doing something. For example, Objc_msgsend (obj, foo):
1, first, through the ISA pointer of obj to find its class;
2, in the class method list to find Foo;
3. If the class does not reach Foo, continue to look for it in the superclass;
4, once found Foo This function, go to implement its implementation imp.
But there is a problem with this implementation, which is inefficient. But a class often has only 20% of functions that are often called, which can account for 80% of the total number of calls. It is not reasonable for each message to traverse one objc_method_list at a time. If you cache a function that is often called, it can greatly improve the efficiency of the function query. This is what another important member of the Objc_class Objc_cache do-after finding Foo, the method_name of Foo is the key and Method_imp is stored as value. When you receive the Foo message again, you can find it directly in the cache and avoid traversing the objc_method_list.
Http://tech.glowing.com/cn/implement-kvo/KVO, KVC realization principle and runtime explanation
Advanced iOS Development Technology Exchange Group: 415239068, Welcome to join US