转换模板内部值问题

时间:2013-07-03 12:05:00

标签: c# .net list generics casting

我无法分享我的代码,基本上我有一个类实现接口,如:

public interface A
{
    void doA();
}

public class B: A
{
    public void doA()
    {
     // Doing A
    }
}

我有一个像这样的A列表:

List<B> list = new List<B>();
list.Add(new B());

现在我想要一个IEnumerable<A>。所以我尝试了这3行:

List<A> listCast = (List<A>)list;
IEnumerable<A> listCastToEnumerable = (IEnumerable<A>)list;
IEnumerable<A> listCastExt = list.Cast<A>();
  1. 第一个出错了:
  2.   

    “错误1无法转换类型   'System.Collections.Generic.List<WindowsFormsApplication1.B>'来   'System.Collections.Generic.List<WindowsFormsApplication1.A>'”。

    1. 第二个没有出错,但得到了InvalidCastException

    2. 第三个工作。

    3. 我的问题是:

      1. 为什么第一行出错而第二行没有?
      2. 为什么前两个内衬无效?
      3. 做这种演员表演的最佳方法是什么?
      4. 是第三条有利于这一点还是有更好的方法

3 个答案:

答案 0 :(得分:1)

让我们分解。

1.为什么第一行出错而第二行没有?

在第二行,你要投射到一个协变的IEnumerable(T)

2.为什么前两个内衬无效?

即使你施放List<B>,它仍然保留其基础类型信息,这意味着它不能保存类型A的不属于B类的项目。

3.做这种演员表演的最佳方法是什么?第三行是好的还是有更好的方法

第三行将List的每个元素转换为类型A并返回类型A的新IEnumerable(T)。这可以迭代到A类的新List中,这将很愉快持有A类的任何元素。

答案 1 :(得分:0)

您也可以

 IEnumerable<A> listoftypeb = list.OfType<A>();

如果你有一个不能输入A的元素,这将给你一个没有错误的A列表

答案 2 :(得分:0)

你需要创建一个IEnumerable(T)并用你列表中的数据填充它,因为 List<B>不是IEnumerable<A>