Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use IList<> to improve performance #262

Open
viceroypenguin opened this issue Mar 1, 2023 · 1 comment
Open

Use IList<> to improve performance #262

viceroypenguin opened this issue Mar 1, 2023 · 1 comment
Labels
enhancement New feature or request
Milestone

Comments

@viceroypenguin
Copy link
Owner

viceroypenguin commented Mar 1, 2023

IList<> has better performance when using a for-loop, as long as .Count is cached before the start of the iteration. Update certain operators to use IList<> over ICollection<>/IEnumerable<>.

// * Summary *

BenchmarkDotNet v0.13.12, Windows 11 (10.0.22621.3447/22H2/2022Update/SunValley2)
12th Gen Intel Core i7-12700H, 1 CPU, 20 logical and 14 physical cores
.NET SDK 9.0.100-preview.3.24204.13
  [Host] : .NET 8.0.4 (8.0.424.16909), X64 RyuJIT AVX2
Method source Mean Error StdDev Allocated
Foreach Syste(...)nt32] [47] 797.1 μs 11.24 μs 10.52 μs 42 B
ForLoop Syste(...)nt32] [47] 468.0 μs 3.35 μs 2.97 μs 1 B
ForLoopCache Syste(...)nt32] [47] 416.6 μs 6.27 μs 5.87 μs 1 B
Foreach Syste(...)nt32] [59] 3,272.8 μs 58.44 μs 54.66 μs 39 B
ForLoop Syste(...)nt32] [59] 6,468.7 μs 74.49 μs 66.03 μs 15 B
ForLoopCache Syste(...)nt32] [59] 3,292.2 μs 54.45 μs 48.27 μs 7 B
Foreach Int32[1000000] 3,606.6 μs 43.21 μs 40.42 μs 39 B
ForLoop Int32[1000000] 4,980.1 μs 50.78 μs 47.50 μs 15 B
ForLoopCache Int32[1000000] 2,543.4 μs 23.93 μs 22.38 μs 7 B
Code
#load "BenchmarkDotNet"

void Main()
{
	RunBenchmark();
}

public IEnumerable<IList<int>> GetSources()
{
	var source = Enumerable.Range(1, 1_000_000);
	yield return source.ToArray();
	yield return source.ToList();
	yield return source.ToImmutableArray();
}

[Benchmark]
[ArgumentsSource(nameof(GetSources))]
public void Foreach(IList<int> source)
{
	var sum = 0;
	foreach (var i in source)
		sum += i;
}

[Benchmark]
[ArgumentsSource(nameof(GetSources))]
public void ForLoop(IList<int> source)
{
	var sum = 0;
	for (var i = 0; i < (uint)source.Count; i++)
		sum += source[i];
}

[Benchmark]
[ArgumentsSource(nameof(GetSources))]
public void ForLoopCache(IList<int> source)
{
	var sum = 0;
	var n = (uint)source.Count;
	for (var i = 0; i < n; i++)
		sum += source[i];
}
@viceroypenguin viceroypenguin added this to the Future milestone Mar 1, 2023
@viceroypenguin viceroypenguin added the enhancement New feature or request label May 4, 2023
@tacosontitan
Copy link
Collaborator

What are these "certain operators" that need to be updated to use IList<>?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants