Skip to content

Read interface IList.Count once rather than per iteration #9962

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

Merged
merged 3 commits into from
May 5, 2019

Conversation

benaadams
Copy link
Member

Cache IList.Count when used as an iteration condition as it is an uninlinable interface call so needs to be evaluated each time.

30M calls for 44k requests to dotnet new mvc homepage; or ~680 calls per request.

image

/cc @rynowak

@rynowak
Copy link
Member

rynowak commented May 4, 2019

😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻 😻

@rynowak
Copy link
Member

rynowak commented May 4, 2019

What's the number of calls after the changes?

@benaadams
Copy link
Member Author

14M for 53.5k requests so ~680 => ~267 per request

image

@rynowak
Copy link
Member

rynowak commented May 4, 2019

awesome!

@rynowak
Copy link
Member

rynowak commented May 4, 2019

It's a shame that the simplest way to implement a collection type leads you down this path - thinking of https://github.com/aspnet/AspNetCore/blob/master/src/Razor/Razor/src/TagHelpers/ReadOnlyTagHelperAttributeList.cs and other types we have that subclass Collection<> or ReadOnlyCollection<>.

I've been thinking about how I want to implement https://github.com/aspnet/AspNetCore/blob/master/src/Http/Http.Abstractions/src/Routing/EndpointMetadataCollection.cs#L100 - because we need to change this in 3.0 to return something better than IEnumerabl<>. I'll probably write a concrete type backed by T[] that implements IReadOnlyList<T> and a struct enumerator.

@rynowak rynowak merged commit 19c9010 into dotnet:master May 5, 2019
@rynowak
Copy link
Member

rynowak commented May 5, 2019

Thanks @benaadams

@benaadams benaadams deleted the IList.Count branch June 10, 2019 12:52
martincostello added a commit to martincostello/aspnetcore that referenced this pull request Jun 15, 2019
Inspired by dotnet#9962, read .Count once rather than once per loop iteration.
pranavkm pushed a commit that referenced this pull request Jun 17, 2019
…ellany (#11253)

* Read interface IList.Count once rather than per iteration

Inspired by #9962, read .Count once rather than once per loop iteration.

* Use nameof() instead of ToString()

Use constant nameof() on enum value, rather than runtime ToString().

* Right-size dictionary

Initialize dictionary with a fixed number of elements to the number of elements it contains.

* Use DisposeAsync()

Use DisposeAsync() on FileBufferingReadStream in input formatters.

* Override DisposeAsync()

Override DisposeAsync() to call DisposeAsync() on the inner stream.

* Use GetValueOrDefault() for content-length

Use GetValueOrDefault() to read the content length once instead of checking HasValue once and Value up to three times.

* Update Microsoft.AspNetCore.WebUtilities.netcoreapp3.0.cs

Add DisposeAsync().

* Use DisposeAsync()

Use DisposeAsync() on transcoding streams as other formatters do.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants