很久以前,我写了一篇关于反思的文章。
这篇文章中的代码仍然是正确的。如你所知,反思是非常昂贵的,但有时是必要的邪恶。然而,它特别昂贵的价值类型,因为装箱和拆箱。
不久前我也写了一篇关于这个话题的文章。
基本上,每当你使用反射,obj-c的价值,并将其包装在一个NSValue对象或NSNumber,如果你正在处理数字。
今天,我将向您展示如何实际跳过拳击和拆箱。虽然它有点棘手,它肯定会加快你的应用程序,如果你使用反射循环通过大量的数据。
为了使主题尽可能简单,我将向您展示如何为double做到这一点。但是,您可以自定义此功能以支持任何其他值类型,尽管您必须预先知道您支持的值类型。
首先,我们需要typedef一个名为 “getDouble” 的方法,它将返回我们的值:
typedef double (* getDouble)(id, SEL);
接下来,我们需要定义一个名为 “helperBlock” 的块,我们将调用它进行反射:
typedef double (^ helperBlock)(NSObject *, SEL, IMP);
现在我们可以创建helperBlock的实例
helperBlock block = ^ double (NSObject * obj,SEL选择器,IMP方法)
{
getDouble f = (getDouble) 方法;
return f(obj,selector);
};
请注意我们如何将IMP作为我们的getDouble方法,以便我们知道返回类型是什么。
让我们创建一个虚拟类,我们将使用这个对:
@ interface ObjectToReflect
@ property(nonatomic, assign)double value;
@ property(nonatomic, assign)NSString * key;
@ end
那么,我们将如何反映和获得价值属性?好吧,让我们假设我们创建了一个 “objecttreflectect” 对象数组。
IMP方法 = 零;
for (数据中的NSObject * obj)
{
if(method = = nil)
method = [obj methodForSelector:getProp];
double val = block(obj, NSSelectorFromString(@ “value”), method);
}
现在你已经反映了你的数据对象。就像我说的,它有点复杂,但希望这有助于简化事情。它肯定会让你的代码更快。
希望这有助于!
史蒂芬·扎哈鲁克 (SteveZ)