使用LINQ语法扫描嵌套字典

时间:2014-05-24 17:08:24

标签: c# linq dictionary

我有这个工作代码:

using System;
using System.IO;
using System.Collections.Generic;
using System.Linq;

public class Example {
    public static void Main(string[] args) {
        var files = new Dictionary<string, Dictionary<string, int>>()
                   { { "file1", new Dictionary<string, int>() { { "A", 1 } } } };
        foreach(var file in files) {
            File.WriteAllLines(file.Key + ".txt", file.Value.Select(
                    item => item.Key + item.Value.ToString("000")).ToArray());
        }
    }
}

但是我想将foreach更改为LINQ语法。我没有尝试过任何工作。

2 个答案:

答案 0 :(得分:2)

这就是你想要的吗?

var files = new Dictionary<string, Dictionary<string, int>>() 
            { { "file1", new Dictionary<string, int>() { { "A", 1 } } } };
files.ForEach(kvp =>
    File.WriteAllLines(kvp.Key + ".txt", kvp.Value.Select(
            item => item.Key + item.Value.ToString("000")).ToArray()));

根据Alexei的评论,IEnumerable.ForEach不是标准的扩展方法,因为它意味着突变,这不是函数式编程的目标。您可以使用辅助方法like this one添加它:

public static void ForEach<T>(
    this IEnumerable<T> source,
    Action<T> action)
{
    foreach (T element in source)
        action(element);
}    

此外,您的原始标题暗示Dictionaries的初始化程序语法很难处理。你可以做些什么来减少大量元素的输入/代码空间量是建立一个匿名对象数组然后ToDictionary()。不幸的是,性能影响很小:

var files = new [] { new { key = "file1", 
                           value = new [] { new {key = "A", value = 1 } } } }
    .ToDictionary(
        _ => _.key, 
        _ => _.value.ToDictionary(x => x.key, x => x.value));

答案 1 :(得分:2)

foreach正是你应该在这里使用的。 LINQ就是查询数据:投影,过滤,排序,分组等等。您正在尝试为已经存在的集合中的每个元素执行操作。

只需使用foreach进行迭代。

ForEach上没有IEnumerable<T>扩展方法的原因有:

主要是关于:

  

不使用ForEach的原因是它模糊了纯功能代码和状态完全命令代码之间的界限。

我可以看到不使用foreach循环的唯一原因是,当您希望使用Parallel.ForEach并行运行您的操作时:

Parallel.ForEach(
    files,
    kvp => File.WriteAllLines(kvp.Key + ".txt", kvp.Value.Select(
               item => item.Key + item.Value.ToString("000")).ToArray()));

ForEach上使用IEnumerable<T>扩展方法是一个糟糕的设计,我建议不要这样做。