iOS运行时runtime获取私有属性和强制更改私有属性,以及获取私有方法

OC是运行时语言,只有在程序运行时,才会去确定对象的类型,并调用类与对象相应的方法。利用runtime机制让我们可以在程序运行时动态修改类、对象中的所有属性、方法,就算是私有方法以及私有属性都是可以动态修改的。本文旨在对runtime的部分特性小试牛刀,更多更全的方法可以参考系统API文件,demo例子可以参见CSDN的runtime高级编程系列文章。

废话少说,上代码:

先看一个Person类:

Person.h

[objc] view plaincopy

  1. import

  2. @interface Person : NSObject

  3. @property (nonatomic,strong) NSString *name;

    • (void)sayHello;
  4. @end

Person.m

[objc] view plaincopy

  1. import "Person.h"

  2. @interface Person()

  3. @property (nonatomic,strong) NSString *address;

  4. @end

  5. @implementation Person

    • (instancetype)init
  6. {

  7. self = [super init];

  8. if (self) {

  9. _address = @"三里屯SOHO";

  10. self.name = @"AirZilong";

  11. }

  12. return self;

  13. }

    • (NSString *)description
  14. {

  15. return [NSString stringWithFormat:@"address: %@, name: %@",self.address,self.name];

  16. }

    • (void)sayHello
  17. {

  18. NSLog(@"hello ,I'm at %@",self.address);

  19. }

    • (void)interface
  20. {

  21. NSLog(@"I'm %@",self.name);

  22. }

  23. @end

控制器controller.m

[objc] view plaincopy

  1. #import "ViewController.h"

  2. import "Person.h"

  3. import

  4. @interface ViewController ()

  5. @end

  6. @implementation ViewController

    • (void)viewDidLoad {
  7. [super viewDidLoad];

  8. Person *onePerson = [[Person alloc] init];

  9. NSLog(@"first time : %@",[onePerson description]);

  10. unsigned int count = 0;

  11. Ivar *members = class_copyIvarList([Person class], &count);

  12. for (int i = 0; i < count; i++)

  13. {

  14. Ivar var = members[i];

  15. const charchar *memberAddress = ivar_getName(var);

  16. const charchar *memberType = ivar_getTypeEncoding(var);

  17. NSLog(@"address = %s ; type = %s",memberAddress,memberType);

  18. }

  19. //对私有变量的更改

  20. Ivar m_address = members[1];

  21. object_setIvar(onePerson, m_address, @"朝阳公园");

  22. NSLog(@"second time : %@",[onePerson description]);

  23. //控制私有函数

  24. [self private];

  25. //

  26. // //添加新方法

  27. // [self addFun];

  28. }

    • (void)private
  29. {

  30. unsigned int count = 0;

  31. Method *memberFuncs = class_copyMethodList([Person class], &count);

  32. for (int i = 0; i < count; i++)

  33. {

  34. SEL address = method_getName(memberFuncs[i]);

  35. NSString *methodName = [NSString stringWithCString:sel_getName(address) encoding:NSUTF8StringEncoding];

  36. NSLog(@"member method : %@",methodName);

  37. }

  38. }

最后打印出来的内容;

2016-03-17 23:55:20.833 Test-RunTime[6531:98356] first time : address: 三里屯****SOHO, name: AirZilong

2016-03-17 23:55:20.833 Test-RunTime[6531:98356] address = _name ; type = @"NSString"

2016-03-17 23:55:20.833 Test-RunTime[6531:98356] address = _address ; type = @"NSString"

2016-03-17 23:55:20.833 Test-RunTime[6531:98356] second time : address: 朝阳公园****, name: AirZilong

2016-03-17 23:55:20.833 Test-RunTime[6531:98356] member method : sayHello

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : address

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : interface

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : description

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : name

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : setName:

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : init

2016-03-17 23:55:20.834 Test-RunTime[6531:98356] member method : setAddress:

是不是很神奇,赶快努力吧!

转于:AirZilong的博客

你可能感兴趣的:(iOS运行时runtime获取私有属性和强制更改私有属性,以及获取私有方法)