今天我正在开展一个项目,我希望为NSArray
的所有实例“替换”替代方法,并且认为某些good old-fashioned method swizzling.不会太困难
我爆发了JRSwizzle和......
[NSArray jr_swizzleMethod:@selector(objectAtIndex:) withMethod:@selector(objectAtIndex_accordingToMe:) error:nil];
为了清楚起见,我将其与NSArray
上的相应类别配对,这是一种名为objectAtIndex_accordingToMe:
的实例方法。
但是,我只是在同一个旧索引上获得相同的旧对象。叹。最终,我发现虽然没有抛出任何错误 - 我不会实现这些结果due to the fact that NSArray
is a class cluster
我想我的问题更多的是不愿意接受“这个”真的是试图覆盖NSArray
方法的终点。我的意思是,来吧这是NSArray
..人们一定想用它来捣乱,不是吗?一个会认为 Apple的基础课程将成为各地流氓的主要目标!
那么,有没有办法改变,别名,monkey-patch,覆盖或以其他方式使用... NSArray等(没有子类化)?
答案 0 :(得分:4)
这不仅仅是一个类集群。 NSArray
免费与CFArray
桥接,您无法调动Core Foundation。所以这一般不太可能奏效。
但是你想要解决什么?如果要添加新方法,请使用类别。他们在类集群上工作很好。修改一些内置在NSArray上的行为似乎是灾难的一个方法(娱乐,因为它可能是一个练习)。
在太之前,你可能想要至少看一下CFArray.c并了解一些底层的东西是如何实现的。
答案 1 :(得分:3)
据推测,你有一个特定的数组,你喜欢这种行为。您可以获取该实例的类对象,无论它是什么,并且很容易调整:
[[myArray class] jr_swizzleMethod:@selector(objectAtIndex:) withMethod:@selector(objectAtIndex_accordingToMe:) error:nil];
NSArray
只有一些具体的子类:
NSArray * trees = [NSArray array];
NSArray * birds = [NSArray arrayWithObjects:@"Albatross", @"Budgerigar", @"Cardinal", nil];
NSMutableArray * dogs = [NSMutableArray arrayWithObjects:@"Airedale", @"Beagle", @"Collie", nil];
NSLog(@"%@ %@ %@", [trees class], [birds class], [dogs class]);
我们获得前两个__NSArrayI
和第三个__NSArrayM
,因此可能(这是非常脆弱)您可以使用运行时函数按名称获取类对象:
[objc_getClass("__NSArrayI") jr_swizzleMethod:@selector(objectAtIndex:) withMethod:@selector(objectAtIndex_accordingToMe:) error:nil];