并行运行简单的LINQ查询

问题描述 投票:19回答:2

我对LINQ和PLINQ还是很陌生。通常,在很多情况下,我通常只使用循环和List.BinarySearch,但我正尽力摆脱这种思维定势。

public class Staff
{
  // ...
  public bool Matches(string searchString)
  {
    // ...
  }
}

使用“正常” LINQ-对不起,我不熟悉该术语-我可以执行以下操作:

var matchedStaff = from s
                     in allStaff
                  where s.Matches(searchString)
                 select s;

但是我想并行执行此操作:

var matchedStaff = allStaff.AsParallel().Select(s => s.Matches(searchString));

[当我检查matchedStaff的类型时,这是bool的列表,这不是我想要的。

首先,我在这里做错什么,其次,如何从该查询返回List<Staff>

public List<Staff> Search(string searchString)
{
  return allStaff.AsParallel().Select(/* something */).AsEnumerable();
}

返回IEnumerable<type>,而不是List<type>

c# linq plinq
2个回答
33
投票

对于您的[[第一个问题,您只需将Select替换为Where

var matchedStaff = allStaff.AsParallel().Where(s => s.Matches(searchString));

[Select是一个投影运算符

,而不是过滤运算符,这就是为什么要得到一个与所有Staff对象从输入序列到IEnumerable<bool>方法返回的布尔的投影相对应的Matches的原因致电。我知道您完全不使用select可能会很直观,因为您似乎更熟悉“查询语法”,其中选择关键字是强制性的,而使用“ lambda语法”则不是这种情况(或“流利的语法” ...不管是什么命名),但是就是这样;)

投影运算符,例如Select

从序列中获取一个元素作为输入,然后将该元素以某种方式转换/投影到另一种类型的元素(此处投影为bool类型)。而过滤运算符,例如Where从序列中获取元素,并根据谓词以输出序列的形式输出元素,或者根本不输出该元素。关于您的

第二个问题

AsEnumerable返回一个IEnumerable,如其名称所示;)如果要获取List<Staff>,则应致电ToList()(如名称所示;)):return allStaff.AsParallel().Select(/* something */).ToList();
希望这会有所帮助。

9
投票
无需放弃常规的LINQ语法即可实现并行性。您可以重写原始查询:

var matchedStaff = from s in allStaff where s.Matches(searchString) select s;

并行LINQ(“PLINQ”)版本为:

var matchedStaff = from s in allStaff.AsParallel() where s.Matches(searchString) select s;

[编写以下内容时,要了解bool的来源:

var matchedStaff = allStaff.AsParallel().Select(s => s.Matches(searchString));

相当于以下查询语法:

var matchedStaff = from s in allStaff.AsParallel() select s.Matches(searchString);

[As stated by darkey,如果要使用C#语法而不是查询语法,则应使用Where()

Where()

© www.soinside.com 2019 - 2024. All rights reserved.