帮助Linq和Dictionary的ContainsKey方法

C J*_*son 0 c# linq linq-to-objects dictionary

我正在编写一个工具,该工具的第一部分是收集公共API中的所有头文件.问题是,两个头文件有重复的文件名(但它们位于不同的文件夹中).这将在创建字典时导致问题.

最初我写了一个foreach循环来收集FileInfo实例到字典中.但是最近我正在学习LINQ,我想将foreach循环转换为LINQ语句.问题是当它执行时,它抱怨重复的文件名.

这是原始代码:

public Dictionary<String, FileDependency> GetSDKFiles(DirectoryInfo dir)
{
    Dictionary<String, FileDependency> list = new Dictionary<String, FileDependency>();
    foreach (FileInfo info in dir.EnumerateFiles("*.h", SearchOption.AllDirectories))
    {
        String key = info.Name.ToLower();
        if (list.ContainsKey(key) == false)
        {
            list.Add(key, new FileDependency(info.FullName));
        }
        else
        {
            Debug.Print("Duplicate key: {0}", info.Name);
            Debug.Print("  File: {0}", info.FullName);
            Debug.Print("  Have: {0}", list[key].FullFileName);
        }
    }

    return list;
}
Run Code Online (Sandbox Code Playgroud)

我尝试过像这样转向LINQ:

public Dictionary<String, FileDependency> GetSDKFilesLINQ(DirectoryInfo dir)
{
    var files = from info in dir.EnumerateFiles("*.h", SearchOption.AllDirectories)
                let key = info.Name.ToLower()
                let dep = new FileDependency(info.FullName)
                select new { key, dep };
    return files.ToDictionary(v => v.key, v => v.dep);
}
Run Code Online (Sandbox Code Playgroud)

但是在运行时我得到了这个:

已添加具有相同键的项目.

在foreach循环中,很容易避免这种情况,因为我调用了ContainsKey方法以确保我没有重复.但是LINQ等价物是什么?

我在哪里使用?- 怎么样?我是否使用团体?- 怎么样?

谢谢.

Ani*_*Ani 5

var files = dir.EnumerateFiles("*.h", SearchOption.AllDirectories)
               .GroupBy(file => file.Name.ToLower())
               .Select(group => new {Key = group.Key, Value = group.First()})
               .ToDictionary(a => a.Key, a => new FileDependency (a.Value.FullName));
Run Code Online (Sandbox Code Playgroud)

如果你有MoreLinq,你可以这样做:

var files =  dir.EnumerateFiles("*.h", SearchOption.AllDirectories)
                .DistinctBy(file => file.Name.ToLower())
                .ToDictionary(file => new FileDependency (a.Value.FullName));
Run Code Online (Sandbox Code Playgroud)

或者,您可以IEqualityComparer为文件编写自己的实现并使用标准Distinct方法.这里的整个问题是Distinct(至少从.NET 3.5开始)没有带有重载,允许将自己的"distinctness"定义作为lambda表达式插入.