Functions of third-party libraries that can be called in OBJC by dynamically running methods
You can use the following method to determine whether the project has introduced a third-party library, if introduced, you can obtain the corresponding method by ntsdkimp the function pointer to execute the code. If it is not introduced, it is not executed.
By obtaining the IMP pointer of the method, the corresponding function can be run, if the imp is empty, the description does not contain the required libraries and symbols.
@interfaceViewcontroller ()@end@implementationViewcontroller- (int) Printonenumber: (int) Number {NSLog (@"Print Number%d", number); returnNumber +1;}+ (NSString *) Numberaddone: (NSString *) num {nsinteger n=[num IntegerValue]; N++; NSString*ret = [NSString stringWithFormat:@"%ld", n]; NSLog (@"%@", ret); returnret;}
As above Viewcontroller contains a
Printonenumber
Numberaddone these two methods,
It is usually possible to execute the corresponding function method via the INT ret = [self printonenumber:1] call, which is complicated by the following imp, but can execute the corresponding code without declaring or referencing the corresponding header file.
- (void) viewdidload {[Super viewdidload]; //additional setup after loading the view, typically from a nib.NSString*methodname =@"Printonenumber:"; IMP Imp=[Ntsdkimp getinstance:self method:methodname]; int(*func) (ID, SEL, ...) = (void*) Imp; if(func) {SEL selector=nsselectorfromstring (methodName); intRET = func (self, selector,4); NSLog (@"%d", ret); } Imp= [Ntsdkimp getclass:@"Viewcontroller"Method@"Numberaddone:"]; ID(*FUNC2) (ID, SEL, ...) = (void*) Imp; if(FUNC2) {SEL selector= Nsselectorfromstring (@"Numberaddone:"); Class ClassA= Nsclassfromstring (@"Viewcontroller"); IDs = Func2 (ClassA, selector,@"4"); NSLog (@"%@", s); }}
If you are returning a nsobject, you need to use the
ID (*FUNC2) (ID, SEL, ...)
Set the format of the Imp
If you are returning the underlying data type (not an instance object), you need to
Int (*FUNC) (ID, SEL, ...)
Set the format of the Imp
The corresponding Ntsdkimp code is as follows:
#import<Foundation/Foundation.h>@interfaceNtsdkimp:nsobject/** * Get the function pointer of class method * * @param className Object * @param methodName method * * @return function pointer*/+ (IMP) GetClass: (NSString *) ClassName method: (NSString *) MethodName;/** * Get the function pointer of the object method * * @param instance Object * @param methodName method * * @return function pointer*/+ (IMP) getinstance: (ID) Instance method: (NSString *) MethodName;/** * Print out the class method to be called * * @param className class name * @param methodName method name * @param arguments parameter list*/+ (void) Logclass: (NSString *) className Runmethod: (NSString *) methodName Withargs: (Nsarray *) arguments;/** * Print out the object method to be called * * @param className class name * @param methodName method name * @param arguments parameter list*/+ (void) Loginstance: (NSString *) InstanceName Runmethod: (NSString *) methodName Withargs: (Nsarray *) arguments;@end
#import "NtSdkIMP.h"#import "NTLog.h"@implementationNtsdkimp+ (IMP) GetClass: (NSString *) ClassName method: (NSString *) methodName {Class ClassA=nsclassfromstring (className); //the class exists if(ClassA) {Ntlog (@"Class%@ Exist", ClassName); SEL selector=nsselectorfromstring (methodName); //there is a corresponding method if([ClassA respondstoselector:selector]) {Ntlog (@"Method%@ Exist", MethodName); IMP Imp=[ClassA Methodforselector:selector]; returnimp; } //there is no corresponding method. Else{Ntlog (@"Method not%@ Exist", MethodName); returnNULL; } } //the class exists Else{Ntlog (@"Class%@ not exist", ClassName); returnNULL; }}+ (IMP) getinstance: (ID) Instance method: (NSString *) MethodName {//Object exists if(instance) {Ntlog (@"Instance%@ Exist", instance); } //object does not exist Else{Ntlog (@"Instance%@ not Exist", instance); returnNULL; } SEL Selector=nsselectorfromstring (methodName); //there are corresponding methods if([instance Respondstoselector:selector]) {Ntlog (@"Method%@ Exist", MethodName); IMP Imp=[instance methodforselector:selector]; returnimp; } //there is no corresponding method Else{Ntlog (@"Method%@ not Exist", MethodName); returnNULL; }}+ (void) Logclass: (NSString *) className Runmethod: (NSString *) methodName Withargs: (Nsarray *) Arguments {ntlog (@"classname:%@", ClassName); Ntlog (@"method:%@", MethodName); for(NSObject *Object incharguments) {Ntlog (@"%@ %@",Object.class,Object); } //The method name queue. If there are no parameters, do not include colons, if there are multiple arguments, there are colons separated, and the last method is named @ ""Nsmutablearray *arrmethod = [Nsmutablearray arraywitharray:[methodname componentsseparatedbystring:@":"]]; //method name does not exist if(Arrmethod.count <1) {Ntlog (@"MethodName is nil"); return; } nsmutablestring*stringmethods =[[Nsmutablestring alloc] init]; Nsuinteger I=0; //with no parameters if(Arrmethod.count = =1) {[Stringmethods appendstring:[arrmethod firstobject]]; } //Multiple Parameters Else { for(NSString *methodinchArrmethod) { if(Method isequaltostring:@""]) { Break;//The last one is @ "", need to remove} [Stringmethods Appendstring:method]; [Stringmethods appendString:@":"]; //parameter is not an empty object if([arguments objectatindex:i]) {[Stringmethods appendstring:[[arguments objectatindex:i] description] ; } //argument is an empty object Else{[Stringmethods appendString:@"Nil"]; } //Add a space if([Arrmethod indexofobject:method]! = arrmethod.count-2) {[Stringmethods appendString:@" "]; } } } //Print out the class method you want to tuneNtlog ("\nrun Class Method: [%@%@]", ClassName, stringmethods);}#pragmaMark Todo:+ (void) Loginstance: (ID) Instance Runmethod: (NSString *) methodName Withargs: (Nsarray *) Arguments {}@end
Code that iOS dynamically executes