2009-07-02 144 views
10

我有一个事件处理程序需要确定一个类型并执行代码,如果它匹配一个特定的类型。最初我们把它转换成一个对象,如果它不是null,我们执行代码,为了加快速度,我使用了反射,实际上它减慢了速度,我不明白为什么。为什么在.NET中投射速度比反射速度快?

这里是一个代码示例

Trace.Write("Starting using Reflection"); 
if (e.Item.GetType() == typeof(GridDataItem)) 
{ 
     bool isWatch = Convert.ToBoolean(e.Item.OwnerTableView.DataKeyValues[e.Item.ItemIndex]["IsWatch"]); 
     if (isWatch) 
     { 
      e.Item.Style["Font-Weight"] = "bold"; 
     } 
} 
Trace.Write("Ending using Reflection"); 
Trace.Write("Starting using Cast"); 
GridDataItem gridItem = e.Item as GridDataItem; 
if (gridItem !=null) 
{ 
    bool isWatch = Convert.ToBoolean(gridItem.OwnerTableView.DataKeyValues[e.Item.ItemIndex]["IsWatch"]); 
    if (isWatch) 
    { 
     gridItem.Style["Font-Weight"] = "bold"; 
    } 
    } 
    Trace.Write("Ending using Cast"); 

这是跟踪输出我得到

Starting using Reflection 0.79137944962406 0.576538 
Ending using Reflection 0.791600842105263 0.000221 
Starting using Cast 0.791623353383459 0.000023 
Ending using Cast  0.791649308270677 0.000026 
Starting using Reflection 0.876253801503759 0.084604 
Ending using Reflection 0.87631790075188 0.000064 
Starting using Cast 0.87633445112782 0.000017 
Ending using Cast  0.87634950075188 0.000015 

这不是很多,但如果我们不得不这样做了很多随着时间的推移它可以增加向上。

+3

随着时间的推移_Everything_可能会加起来。除非你有证据表明这个实际上是随着时间的推移累加的,否则不要强调它。 – 2009-07-02 18:25:43

+0

这是关于最佳实践的更多信息,如果铸造速度更快,那么我应该使用铸造而不是反射 – 2009-07-02 18:47:10

回答

15

由于您在查询程序集的元数据,因此反射速度很慢,而铸造只是简单地改变了您所引用的对象的类型。

程序集的元数据是一个有用的信息存储区,但该信息最好在编译时间处使用,而不是在执行时。该元数据被编译器用于静态类型检查(等等)。您正在使用相同的元数据在执行时查找类型信息(如果没有其他选择,这很好),这比铸造速度慢得多。

3

反射必须在运行时去确定对象在运行时具有哪些属性等。投射告诉应用程序它应该期望一个对象具有X属性并且应该以某种方式运行。

2

投射告诉运行时你“知道”一个特定对象的类型。虽然您可能会错误,但运行时相信您并且不需要花费额外的时间去检查程序集的元数据。

1

为什么不使用is operator?我认为它更具可读性,因为你没有明确的演员表,然后检查。它只是检查变量的类型是否正确。

if (e.Item is GridDataItem) 
{ 
    bool isWatch = Convert.ToBoolean(e.Item.OwnerTableView.DataKeyValues[e.Item.ItemIndex]["IsWatch"]); 
    if (isWatch) 
    { 
     e.Item.Style["Font-Weight"] = "bold"; 
    } 
} 
0

那么我想一个简短的答案,最佳实践部分将永远不会使用反射,如果你可以得到与常规代码相同的结果。

在优化代码时,通常估计优化所花费的时间会带来最大的性能提升,这通常是一个好主意。在语言本地重新实现操作符很少会在该列表的顶部

1

可以在运行时执行整型比较,但反射涉及完整的方法调用。

相关问题