对于ForAll对象,正确的Dictionary方法是什么?我正在学习Linq类型的迭代(下面的方法1),但是不能让它工作。旧的foreach循环可以工作(下面是方法2)。尽管在类似的问题上有许多答案,例如this question,但我没有看到Linq迭代的解决方案。
字典似乎有获取所有键或所有值的方法,可以在Linq迭代中使用,但不能获得所有的KeyValuePairs。奇怪!
我对GetEnumeration()做了一些摆弄,但运气不佳。
AsParallel()方法似乎是解决方案,找到了here,但我只得到了一个构建错误:字典不包含AsParallel的定义。
可以说,方法2没有那么多行源,但对我来说,方法1的Linq迭代仍然更简单、更直接、更优雅。
还有一个简单的方法让方法1起作用吗?
版本:.Net框架4.5.2
using System.Linq;//AsParallel, ToList
using System.Collections.Generic;//Dictionary
using System.Xml.Linq;//XElement
using System.IO;//Path, Dir, File
public Dictionary<string, string> DictUserConfig = new Dictionary<string, string>();
public void SaveFile(string FileName)
{
XDocument XDConf = new XDocument(new XDeclaration("1.0", "utf-8", "yes"));
#if true//method 1: problem: Dictionary does not have a .ForAll or .ForEach method, or .GetEnumerator().ForAll(x => ...)
XDConf.Add(
new XElement("settings",
DictUserConfig.ForEach(x =>
new XElement("add",
new XAttribute("key", x.Key),
new XAttribute("value", x.Value)))));
#else//method 2: works
XElement XSettings = new XElement("settings");
XDConf.Add(XSettings);
foreach (KeyValuePair<string, string> x in DictUserConfig)
{
XSettings.Add(
new XElement("add",
new XAttribute("key", x.Key),
new XAttribute("value", x.Value)));
}
#endif
XDConf.Save(FileName);
return;
}更新:我发现了一个问题:丢失了using System.Linq,这是一段时间前我不需要的时候删除的。通过测试我的帖子中的几个有用的评论发现。
现在更容易将问题概括为:
这样做是可行的:
DictUserConfig.ToList<KeyValuePair<string, string>>().ForEach(x => Console.WriteLine(x.Key + x.Value));
DictUserConfig.AsParallel().ForAll(x => Console.WriteLine(x.Key + x.Value));但这是行不通的:
XElement XE1 = (XElement)DictUserConfig.ToList<KeyValuePair<string, string>>().ForEach(x => new XElement(x.Key, x.Value));
XElement XE2 = DictUserConfig.AsParallel().ForEach(x => new XElement(x.Key, x.Value));原因是,我想,ToList和AsParallel不会将ForEach的结果返回给this。生成错误是:无法将void转换为object (或XElement)。因此,唯一的“解决方案”似乎是自己使用一行程序创建ForEach,它已经显示为解决方案,但要注意返回一个XElement对象。
在测试了最后的答案之后,我想指出的是,讨论并不是关于foreach相对于ForEach的相对值,而是讨论了选择的真正解决方案。而且,foreach更多的是使某些事情发生的Fortran方式,以及ForEach,特别是Select,而不是关于您想要实现的目标。
我要感谢大家的评论和回答,我今天从中学到了一些东西。
发布于 2016-02-22 15:19:43
您可以使用ToList扩展方法来获得与ForEach方法兼容的KeyValuePairs列表。
Dictionary<string, int> testDict = new Dictionary<string, int>();
testDict.Add("one", 1);
testDict.Add("two", 2);
testDict.Add("three", 3);
testDict.ToList<KeyValuePair<string, int>>().ForEach(x => Console.WriteLine(x.Key));DotNetFiddle这里:https://dotnetfiddle.net/5rRGZc
不过,我同意樱花的说法,即正常的预见可能是更好的选择。
发布于 2016-02-22 15:14:43
ForEach()是List<T>类的一种特殊方法。
但是您可以创建自己的Dictionary<TKey, TVakue>扩展程序方法。
public static class DictionaryExtensions
{
public static void ForEach<TKey, TValue>(this Dictionary<TKey, TValue> dict, Action<KeyValuePair<TKey, TValue>> action)
{
foreach (var item in dict)
action(item);
}
}然后像这样使用它:
XElement XSettings = new XElement("settings");
DictUserConfig.ForEach(x =>
XSettings.Add(new XElement("add",
new XAttribute("key", (string)x.Key),
new XAttribute("value", (string)x.Value))));更新
使用方法1,则可以使用如下所示的扩展器:
public static IEnumerable<TResult> ForEach<TKey, TValue, TResult>(this Dictionary<TKey, TValue> dict, Func<KeyValuePair<TKey, TValue>, TResult> func)
{
foreach (var item in dict)
yield return func(item);
}那么方法1将是:
XDConf.Add(new XElement("settings",
DictUserConfig.ForEach(x =>
new XElement("add", new XAttribute("key", x.Key),
new XAttribute("value", x.Value))).ToArray()));可能Cast<object>()在ToArray()之前是必需的。
https://stackoverflow.com/questions/35556999
复制相似问题