1. Overview
OC is a full-dynamic language, and all OC implementations are based on Runtime
The type of the object is determined only when the program is running, and the corresponding method of the class and object is called.
2. Run-time mechanism
Run-time mechanism is developed in C + +, is a set of Apple open-source framework
OC is based on the language of the runtime development
3. Application Scenarios
The runtime gets the properties of the class dynamically
Main applications:
- Dictionary to Model frame Mjextension,jsonmodel
- Use
关联对象
to add attributes to a category
交换方法
methods of using interception systems or other frameworks
- Myth: The less technology you use, the more efficient the framework will be
Import Header File
#import <objc/runtime.h>
4. Example
Add a category to NSObject
////NSOBJECT+EXTENSION.M//#Import "Nsobject+extension.h"#Import<objc/runtime.h>@implementationNSObject (Extension)Const Char*propertieskey ="Propertieskey";Const Char*methodskey ="Methodskey";Const Char*protocolkey ="Protocolkey";/// Dictionary turn model method+ (Instancetype) objectwithdict: (Nsdictionary *) dict{id obj = [[Self alloc] init];//Get Property listNsarray *properties = [self propertylist];//Traversal property array for(NSString *key in properties) {//Determine if this key is included in the dictionary if(Dict[key]! = nil) {//Use KVC to set property values[obj Setvalue:dict[key] forkeypath:key]; } }returnobj;}/** If you can automatically generate this array, it's OK! If you want to dynamically get the properties of a class, you need to use the Class_copyivarlist member variable to the runtime mechanism, prompting that there are many third-party frameworks that use Ivar to get more information but: in Swift, the use of Ivar is very unstable due to the grammatical structure changes. It often crashes! Class_copypropertylist Property Class_copymethodlist Method Class_copyprotocollist protocol * //// Returns a list of properties for the class+ (Nsarray *) propertylist {//0. Determine if there is an associated object, and if so, return directly the/** parameter 1> the property associated with the object 2> key * /Nsarray *plist = Objc_getassociatedobject (self, propertieskey);if(plist) {returnPlist }//1. Get Properties of ' class ' /** The Count pointer of the 1> Class 2> property * /UnsignedintCount =0;the//return value is an array of all properties Obj_property_objc_property_t *list = Class_copypropertylist ([self class], &count);//Create an array of storage propertiesNsmutablearray *arraym = [Nsmutablearray arraywithcapacity:count]; for(inti =0; I < count; ++i) {//Get Propertiesobjc_property_t pty = list[i];//Get property name Const Char*cname = Property_getname (pty); [Arraym addobject:[nsstring Stringwithutf8string:cname]; }//Release property arrayFree (list);//Set Association object /** 1> The associated object 2> the key 3> property of the associated object 4> the way the property is held, copy, Reatin * /Objc_setassociatedobject (self, propertieskey, Arraym, objc_association_copy_nonatomic);returnArraym.copy;}/// Returns a list of methods for the class+ (Nsarray *) MethodList {//0. Determine if there is a dependency relationshipNsarray *mlist = Objc_getassociatedobject (self, methodskey);if(mlist) {returnMlist; } unsignedintCount =0;//1. Get a list of methodsMethod *list = Class_copymethodlist ([self class], &count);//Storage method ArrayNsmutablearray *arraym = [Nsmutablearray arraywithcapacity:count]; for(inti =0; I < count; ++i) {//Get methodmethod = List[i];//Get method nameSEL Mname = Method_getname (method); [Arraym Addobject:nsstringfromselector (Mname)]; }//release arrayFree (list);//Set dependenciesObjc_setassociatedobject (self, methodskey, Arraym, objc_association_copy_nonatomic);returnArraym.copy;}/// Returns a list of implementation protocols for the class+ (Nsarray *) protocollist{//0. Determine if there is a dependency relationshipNsarray *plist = Objc_getassociatedobject (self, protocolkey);if(pList) {returnPList; } unsignedintCount =0;//2. Get the list of agreementsProtocol * __unsafe_unretained *list = Class_copyprotocollist ([self class], &count);//Create an array of protocolsNsmutablearray *arraym = [Nsmutablearray arraywithcapacity:count]; for(inti =0; I < count; ++i) {//Get agreementProtocol * __unsafe_unretained prot = list[i];Const Char*pname = Protocol_getname (prot); [Arraym addobject:[nsstring Stringwithutf8string:pname]; }returnArraym;}@end
IOS Runtime (runtime) mechanism