如何在我的实现IEnumerable <Foo>的Dictionary包装器类中实现IEnumerable?

Tim*_*man 7 c# ienumerable

我正在尝试为a创建一个包装器Dictionary<String,Foo>.

Dictionary<String,Foo>实现IEnumerable<KeyValuePair<String,Foo>>,但我希望我的包装类实现IEnumerable<Foo>.所以我尝试了这个:

public class FooCollection : IEnumerable<Foo>
{
    private Dictionary<string, Foo> fooDictionary = new Dictionary<string, Foo>();

    public IEnumerator<Foo> GetEnumerator()
    {
        return fooDictionary.Values.GetEnumerator();
    }

    // Other wrapper methods omitted

}
Run Code Online (Sandbox Code Playgroud)

但是我收到此错误:

'FooCollection'没有实现接口成员'System.Collections.IEnumerable.GetEnumerator()'.'FooCollection.GetEnumerator()'无法实现'System.Collections.IEnumerable.GetEnumerator()',因为它没有匹配的返回类型'System.Collections.IEnumerator'.

但是我不明白这个错误,因为FooCollection.GetEnumerator()返回一个IEnumerator<Foo>,而且IEnumerator<Foo>是一个IEnumerator.

编辑:

明确实施IEnumerator.GetEnumerator()工作的解决方案.但是我现在想知道为什么当我"去定义"时,List<T>我只看到一个GetEnumerator的定义: public List<T>.Enumerator GetEnumerator();

显然,List<T>可以有一个GetEnumerator返回的东西,同时实现方法IEnumerator<T>IEnumerator,但我必须为每一个方法?

编辑:

正如下面LukeH所回答的那样,List<T> 确实包含了显式接口实现.显然,Visual Studio在从元数据生成方法存根时不会列出那些.(请参阅前一个问题:为什么VS Metadata视图不显示显式接口实现的成员)

在发布此问题之前,我曾尝试检查List<T>(通过Visual Studio中的"转到定义")以查看是否需要实现多个版本的GetEnumerator.我想这不是最可靠的检查方式.

无论如何,我将此标记为已回答.谢谢你的帮助.

Mat*_*ott 12

添加以下显式接口实现:

IEnumerator IEnumerable.GetEnumerator()
{
    return this.GetEnumerator();
}
Run Code Online (Sandbox Code Playgroud)

虽然IEnumerator<T>是一个IEnumerator,具体的IEnumerable退货合同IEnumerator,而不是IEnumerator<T>


Kei*_*thS 6

实现时IEnumerable<T>,您还必须明确实现IEnumerable.GetEnumerator().泛型接口的方法本身作为非泛型方法契约的实现无效.你可以有一个调用另一个,或者因为你有一个你正在使用的枚举器的子对象,只需复制/粘贴;

using System.Collections;
using System.Collections.Generic;

public class FooCollection : IEnumerable<Foo>
{
    private Dictionary<string, Foo> fooDictionary = new Dictionary<string, Foo>();

    public IEnumerator<Foo> GetEnumerator()
    {
        return fooDictionary.Values.GetEnumerator();
    }

    IEnumerator IEnumerable.GetEnumerator()
    {
        //forces use of the non-generic implementation on the Values collection
        return ((IEnumerable)fooDictionary.Values).GetEnumerator();
    }

    // Other wrapper methods omitted

}
Run Code Online (Sandbox Code Playgroud)