为什么我不能将linq的Cast与用户定义的强制转换一起使用,但我可以将它与Select呼叫一起使用?

时间:2013-03-04 20:58:19

标签: c# linq casting

我最近在使用用户定义的强制转换(强制转换运算符重载)和linq的Cast方法时遇到了问题。

我在SO处找到了关于我的问题的similar question,我还找到了一个link来解释它。我的问题解决了。

但有些事让我感到疑惑:

为什么这不起作用:

foolist.Cast<bar>(); // throws InvalidCastException

虽然这有效:

foolist.Select(f => (bar)f).ToList(); // works fine

我认为这与每种方法的实施有关。如果是这样,Cast方法不能具有与Select类似的实现,允许它与用户定义的强制转换一起使用(因为这有点预期)。

注意:我不是在问为什么会失败。我问为什么Cast方法是以失败的方式编写的。

1 个答案:

答案 0 :(得分:0)

原因是Cast方法在通用上下文中执行强制转换

IEnumerable<T> Cast<T>(this IEnumerable e) {
  foreach (object cur in e) { 
    return (T)cur;
  }
}

在这个确切的点上验证并发出实际的铸造逻辑。这一点在一个通用函数中,并且不知道最终实例化类型T的用户定义的转换。它可以访问的是标准的CLR样式转换。

在第二个示例中,您正在对真实类型(不是泛型类型参数)进行强制转换。因此,C#编译器可以访问该对象上的所有用户定义的转换,并可以插入最合适的转换。