gpt4 book ai didi

c# - Enumerable.Range 与 for 循环的性能

转载 作者:行者123 更新时间:2023-12-02 15:00:44 33 4
gpt4 key购买 nike

我想知道使用 Enumerable.Range 与使用 foreach 循环相比,性能开销是多少。例如:

var stringArray = Enumerable.Range(0, 4).Select(i => string.Empty).ToArray();

VS。

var stringArray = new string[4];
for (int i = 0; i < formatted.Length; i++)
{
stringArray[i] = string.Empty;
}

我发现了这些问题:

  1. Why is Enumerable.Range faster than a direct yield loop?

  2. Enumerable.Range implementation

  3. Thoughts on foreach with Enumerable.Range vs traditional for loop

但我担心最后的 Select 那么我实际上可能会循环两次。不过,我喜欢使用 Range 选项的优雅。

最佳答案

根据以下测试,for更高效:(以毫秒为单位,差异为 +-3 毫秒 - 这是微不足道的..)

var watch = System.Diagnostics.Stopwatch.StartNew();
var stringArra1y = Enumerable.Range(0, 4).Select(i => string.Empty).ToArray();
watch.Stop();
Console.WriteLine(watch.ElapsedTicks); //3305

watch = System.Diagnostics.Stopwatch.StartNew();
var stringArray2 = new string[4];
for (int i = 0; i < stringArray2.Length; i++)
{
stringArray2[i] = string.Empty;
}
watch.Stop();
Console.WriteLine(watch.ElapsedTicks); //1

但是您可以不使用 Enumerable.Range().Select使用.Repeat :

var watch = System.Diagnostics.Stopwatch.StartNew();
var stringArra1y = Enumerable.Repeat(string.Empty, 4).ToArray();
watch.Stop();
Console.WriteLine(watch.ElapsedTicks); //391

说完上述内容后,请注意您在这里谈论的是非常小的集合(4 项)。在较大的集合中,尤其是当您删除 .ToArray() 时它的行为不一样:

var watch = System.Diagnostics.Stopwatch.StartNew();
var stringArra1y = Enumerable.Repeat(string.Empty, 100000);
watch.Stop();
Console.WriteLine(watch.ElapsedTicks); //360


watch = System.Diagnostics.Stopwatch.StartNew();
var stringArray2 = new string[100000];
for (int i = 0; i < stringArray2.Length; i++)
{
stringArray2[i] = string.Empty;
}
watch.Stop();
Console.WriteLine(watch.ElapsedTicks); //1335
<小时/>

But I fear with the Select at the end then I might be, in effect, loop twice

纵观Reference Source两者都是.RangeRepeat是用 yield return 实现的:

static IEnumerable<int> RangeIterator(int start, int count) {
for (int i = 0; i < count; i++) yield return start + i;
}

所以它也延迟执行,就像.Select一样这意味着它不会循环两次。

不是使用Stopwatch每次运行返回不同的结果,但总体思路如上所示

IMO,特别是在小型集合的情况下,优先考虑可读性而不是这些微小的性能改进。当您已经遇到性能问题时,只有在钓到更大的鱼之后(例如在 for 上嵌套 List<> 循环而不是使用 HashSet<> ),才能处理类似的事情。

关于c# - Enumerable.Range 与 for 循环的性能,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40129813/

33 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com