IEnumerable <int>还需要非泛型IEnumerator?</int>

时间:2011-11-27 14:36:09

标签: c# .net generics ienumerable

3个问题:

1)为什么输出来自 NON 泛型函数?

2)为什么我来实现NON泛型函数?

3)如果我想查看通用函数输出(int的),我需要做什么?

enter image description here

3 个答案:

答案 0 :(得分:8)

  1. foreach关键字不要求集合实现IEnumerable;相反,它会调用任何已定义的GetEnumerator方法。

  2. IEnumerable<T>出于兼容性原因实施IEnumerable

  3. 您应该明确地实施IEnumerable.GetEnumerator()并使常规方法返回IEnumerator<T>

  4. 如果类具有正常的GetEnumerator()方法(而不是显式接口实现),编译器将调用它。
    规范说:

      
        
    • 否则,确定类型X是否具有适当的GetEnumerator方法:   
          
      • 使用标识符GetEnumerator对类型X执行成员查找,而不使用类型参数。如果成员查找没有产生匹配,   或者它产生歧义,或产生不是方法的匹配   group,检查如下所述的可枚举接口。它是   建议在成员查找生成时发出警告   除方法组或不匹配的任何内容。
      •   
      • 使用生成的方法组和空参数列表执行重载解析。如果重载决策导致否   适用的方法,导致歧义,或结果单一   最好的方法,但该方法是静态的或不公开的,检查   如下所述的可枚举接口。建议一个   如果重载决议产生除了一个以外的任   明确的公共实例方法或没有适用的方法。
      •   
      • [...]
      •   
    •   
    • 否则,请检查可枚举的界面:
    •   

答案 1 :(得分:6)

1)输出来自非泛型函数,因为它是隐式定义的(并且通用函数是显式定义的)。

2)IEnumerable<T>继承自IEnumerable,因此从IEnumerable<T>继承的任何类型都必须实现IEnumerable的成员

3)使通用定义隐式,非通用定义明确,例如

public class Class1 : IEnumerable<int>
{
    public IEnumerator<int> GetEnumerator()
    {
        yield return 1;
        yield return 2;
        yield return 3;
        yield return 4;
    }

    IEnumerator IEnumerable.GetEnumerator()
    {
        return this.GetEnumerator();
    }
}

请注意,您可以从非泛型方法返回通用枚举器,因为IEnumerator<T>继承自IEnumerator

答案 2 :(得分:3)

您需要同时实现这两项,因为IEnumerable<T>派生自IEnumerable。要调用显式实现的方法,您需要转换为该接口。

但通常你会显式地实现非泛型方法和隐式的泛型方法。那样foreach将使用泛型方法。 foreach对集合的类型使用GetEnumerator()方法,如果此方法不存在,则仅回退到接口方法。

典型的实施是:

public IEnumerator<int> GetEnumerator()
{
   ...
}

System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
  return GetEnumerator();//Forward to strongly typed version
}