Linq List()。您不需要像您想象的那样需要它,它可能会对性能和内存使用产生严重的负面影响

Linq List()。您不需要像您想象的那样需要它,它可能会对性能和内存使用产生严重的负面影响,linq,c#-3.0,enumerable,Linq,C# 3.0,Enumerable,您正在寻找目前仅存在于列表通用集合中的一直难以捉摸的ForEach。关于微软是否应该将其添加为LINQ方法,网上有很多讨论。目前,您必须推出自己的: public static void ForEach<T>(this IEnumerable<T> value, Action<T> action) { foreach (T item in value) { action(item); } } publicstaticvoidforeach

您正在寻找目前仅存在于列表通用集合中的一直难以捉摸的ForEach。关于微软是否应该将其添加为LINQ方法,网上有很多讨论。目前,您必须推出自己的:

public static void ForEach<T>(this IEnumerable<T> value, Action<T> action)
{
  foreach (T item in value)
  {
    action(item);
  }
}
publicstaticvoidforeach(此IEnumerable值,Action)
{
foreach(价值中的T项)
{
行动(项目);
}
}

虽然
All()
方法提供了类似的功能,但它的用例是对每个项执行谓词测试,而不是操作。当然,可以说服它执行其他任务,但这会在一定程度上改变语义,并使其他人更难解释您的代码(即,这是将
All()
用于谓词测试还是操作?)。

列表外有一个ForEach方法。您可以通过调用.ToList()方法将可枚举项转换为List,然后在此基础上调用ForEach方法

或者,我听说有人用IEnumerable定义自己的ForEach方法。这可以通过基本上调用ForEach方法来实现,但可以将其包装在扩展方法中:

public static class IEnumerableExtensions
{
    public static IEnumerable<T> ForEach<T>(this IEnumerable<T> _this, Action<T> del)
    {
        List<T> list = _this.ToList();
        list.ForEach(del);
        return list;
    }
}
公共静态类IEnumerableExtensions
{
公共静态IEnumerable ForEach(this IEnumerable\u this,Action del)
{
List=_this.ToList();
列表。ForEach(del);
退货清单;
}
}

使用LINQ和IEnumerable无法立即执行此操作-您需要实现自己的扩展方法,或者使用LINQ将枚举强制转换为数组,然后调用array.ForEach():


请注意,由于值类型和结构的工作方式,如果集合是值类型,并且您以这种方式修改集合的元素,则不会对原始集合的元素产生任何影响。

不幸的是,在当前版本的LINQ中没有内置的方法来执行此操作。框架团队忽略了添加.ForEach扩展方法。在下面的博客上有一个关于这件事的很好的讨论

不过,添加一个是相当容易的

public static void ForEach<T>(this IEnumerable<T> enumerable, Action<T> action) {
  foreach ( var cur in enumerable ) {
    action(cur);
  }
}
publicstaticvoidforeach(此IEnumerable可枚举,操作){
foreach(可枚举中的var cur){
行动(cur);
}
}

因为LINQ被设计成一种查询功能而不是更新功能,所以您找不到在IEnumerable上执行方法的扩展,因为这将允许您执行方法(可能有副作用)。在这种情况下,你不妨坚持下去

foreach(名称中的字符串名称)
Console.WriteLine(名称)


一种快速简便的方法是:

Names.ToList().ForEach(e => ...);

您也可以使用标准的
foreach
关键字,只需将其格式化为一行:

foreach(var n in Names.Where(blahblah)) DoStuff(n);
抱歉,我认为这个选项应该在这里:)

使用并行Linq:


前面提到的Names.AsParallel().ForAll(name=>…)

ForEach扩展将进行修复

当前问题的提示是如何执行迭代器

[我确实尝试了Select(s=>{Console.WriteLine(s);returns;}),但它没有打印任何内容。]

检查这个

_=Names.Select(s=>{Console.WriteLine;返回0;}).Count()


试试看

Downvoted:只有当谓词继续返回“true”时,才会处理所有项。如果你正在执行一个返回布尔值的方法,那么很容易在没有意识到的情况下意外引入错误。@PeterMorris我相信他的意思是,你可以使用lambda做任何你想做的事情,当你执行完代码后,只会返回true。在这种情况下,您可能需要使用需要大括号的lambda语句。如果您只想使用内置功能并保留惰性计算,那么这是一个不错的解决方案。@AlexJorgenson.All()应该是没有副作用的,这不是一个好方法,因为它的目的是为了某些东西else@Peter莫里斯:当然。在我完全接受这一点之前,我写了这篇文章。我了解linq操作符,但对它们背后的函数编程根源了解较少。今天,我同意哦。。。foreach的另一个抱怨是没有返回序列。但是,如果您需要,我会研究返回新对象(无副作用)的
Select()
,而不是
All()
。七年是很长的时间;)这将迫使完整的序列求值占用临时列表中每个元素的内存。我会在任何时候使用IEnumerable上的扩展方法,以尽可能长时间地保留惰性求值属性。如果要添加它,我更喜欢它。包括执行Func操作并返回IEnumerable的重载。即使已经可以用Select完成。如果这是您的用例,您当然可以编写一个来完成。使用All将是一个坏主意-如果这些Func中的任何一个返回false,那么执行将结束。是的,这是不使用它的另一个很好的理由。这不是懒惰,是吗?因此它会立即计算查询。与普通的foreach相比没有什么真正的优势。ToList()将计算IEnumerable中的每个节点,这意味着任何延迟计算都是在该点进行的。我宁愿通过自己的扩展方法来尽可能晚地结束这个过程。对不起,伙计们,我选择了不受欢迎的方法。我理解丢失惰性评估的缺点,但当我在列表上做ForEach时,我希望它现在就发生,因此不再懒散没有什么好处。扩展方法更好,而且可能更快,但这对我来说“有点”更标准,而且足够短,可以打字。谢谢你,杰!这有一个大问题。如果不列出,则所有对象必须同时存在于内存中。如果源是DB,则至少使用IEnumerable对象m
myList = myList.Select(item => new SomeType(item.value1, item.value2 *4)).ToList();
public static void ForEach<T>(this IEnumerable<T> value, Action<T> action)
{
  foreach (T item in value)
  {
    action(item);
  }
}
public static class IEnumerableExtensions
{
    public static IEnumerable<T> ForEach<T>(this IEnumerable<T> _this, Action<T> del)
    {
        List<T> list = _this.ToList();
        list.ForEach(del);
        return list;
    }
}
Array.ForEach(MyCollection.ToArray(), x => x.YourMethod());
public static void ForEach<T>(this IEnumerable<T> enumerable, Action<T> action) {
  foreach ( var cur in enumerable ) {
    action(cur);
  }
}
Names.ToList().ForEach(e => ...);
foreach(var n in Names.Where(blahblah)) DoStuff(n);