我从ac#book获得了这个代码:
int minSize = 10000;
var bigFiles = from file in GetAllFilesInDirectory(@"c:\")
where new FileInfo(file).Length > minSize
select file;
var filesOver10k = bigFiles.ToArray();
minSize = 100000;
var filesOver100k = bigFiles.ToArray();
minSize = 1000000;
var filesOver1MB = bigFiles.ToArray();
minSize = 10000000;
var filesOver10MB = bigFiles.ToArray();
Run Code Online (Sandbox Code Playgroud)
作者说,每次调用ToArray()时,它都会重新评估查询.我想做类似的事情.我需要查询书中每个字母的使用次数; 目前我正在使用这样的东西:
string alphabet="abcdefghijklmnopqrstuvwxyz";
foreach(char a in alphabet)
{
var stat_letter=book2.book.Sum(b=>b.chapter.Sum(l=>l.line.Sum(w=>w.word.ToLower().Count(c=>c.Equals(a)))));
Console.WriteLine(a + ":" + stat_letter.ToString() );
}
Run Code Online (Sandbox Code Playgroud)
我得到的输出:
a: 31278
b: 6263
c: 14561
[...]
Run Code Online (Sandbox Code Playgroud)
我想把它改成像书的例子一样工作:
char q = 'a';
var stat_letter = book2.book.Sum(b=>b.chapter.Sum(l=>l.line.Sum(w=>w.word.ToLower().Count(c=>c.Equals(q)))));
string alphabet="abcdefghijklmnopqrstuvwxyz";
foreach(char a in alphabet)
{
q=a;
Console.WriteLine(q + ":" + stat_letter.ToString() );
}
Run Code Online (Sandbox Code Playgroud)
我得到的输出:
a: 31278
b: 31278
c: 31278
[...]
Run Code Online (Sandbox Code Playgroud)
在这种情况下,查询似乎不会重新评估.有没有办法强迫它?实际上我的动机是检查它是否会加速程序的执行,所以如果你认为它不会,那也是我想知道的事情......
Sum返回一个int(使用你选择的重载)而不是IEnumerable.这意味着它会立即进行评估,因为它需要它int.a的值int不能推迟.
虽然有几种方法可以重新构建代码以延迟执行,但我更喜欢做的是创建一个方法(或者一个lambda,相同的概念),根据您的输入计算您想要的值,而不是改变查询所依赖的变量.
Func<char, int> computeLetterCount = letter => book2.book.Sum(
b=>b.chapter.Sum(
l=>l.line.Sum(
w=>w.word.ToLower().Count(c=>c.Equals(letter)))));
Run Code Online (Sandbox Code Playgroud)
你现在可以写:
foreach(char a in alphabet)
{
Console.WriteLine(a + ":" + computeLetterCount(a) );
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
279 次 |
| 最近记录: |