plinq select count其中所有函数评估为true

时间:2012-11-06 17:19:21

标签: .net plinq

我有一组数据全部加倍: 100行20列

我将数据拉入IEnumerable列表,其中包含:

var RowsOfData = File.ReadLines(dll.Globals.OutputDir +     dll.Globals.filename).Select(a => a.Split(',').ToList());

var FilteredRowsToday = (from n in RowsOfData
       where n[1] == 1
       orderby n[0] descending
       select n);

然后我有一组函数,它们对每个数据行进行简单检查,每个函数返回一个Bool。 我想要的是每个函数评估为真的行数。 然后当我扩展我的项目时,如果可能的话,我希望并行处理这个asap,我试过了:

foreach (var row in FilteredRowsToday) {  
is f1() true, is f2() true 
etc
}

似乎很慢 我试图并行做

foreach (var row in FilteredRowsToday.AsParallel())

没有更快

我现在想的是:

var TotalTrue = FilteredRowsToday.Select(item => f1() & f2() & f3()).Count();

我可以预先处理数据,以便将每个函数的评估结果作为一种二进制网格提供,如果这是一个更好的说明点吗?

F1, f2, f3 etc
1, 0, 0 row 1
1, 1, 1 row 2 etc
建议欢迎!

2 个答案:

答案 0 :(得分:1)

如果您只对所有三个函数评估为真的计数感兴趣,那么这应该足够了:

var TotalTrue = FilteredRowsToday.Count(item => f1() & f2() & f3());

至于为什么它很慢,你的功能可能就是背后的原因。

您可以尝试仅评估行,直到所有三个函数都返回true,或者至少其中一个函数返回false,例如。

var TotalTrue = FilteredRowsToday.Count(item => f1() && f2() && f3());

即。如果f1()的评估结果为false,那么请不要再进行其余的验证。

UPDATE:如果您的函数没有进行任何资源密集型检查,那么并行LINQ对您没有多大帮助(更多信息here)。

答案 1 :(得分:0)

我看到你正在读取文件,这是一种以逗号分隔的文件。 如果您在阅读时从文件中产生记录,它将允许您处理它们,直到您等待下一次阅读。

private IEnumerable<string> GetRecords(string fileName) {
    using (StreamReader reader = File.OpenText(fileName))
            {
                string line = reader.ReadLine();
                while (line != null)
                {   
                   yield return line.Split(',');
                   line = reader.ReadLine();
                 }
             }
}

您还需要花费一些时间将Split的结果转换为已List的{​​{1}},并且具有执行查询所需的索引权限。

我还建议应用之前建议的优化,例如使用array代替.Count(item => f1() & f2() & f3());

尽管如此,我不相信任何这种优化都会带来如此少量数据的任何改进。如果您发布有关处理部分代码的一些细节,我想我们可以帮助您更好。