-
Notifications
You must be signed in to change notification settings - Fork 4.1k
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
Cleanup/perf in creating member maps. #67997
Conversation
if (builder != null) | ||
static ImmutableArray<TNamespaceOrTypeSymbol> createMembers(object value) | ||
{ | ||
if (value is ArrayBuilder<TNamespaceOrTypeSymbol> builder) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no need for 'hasNamespaces' flag and complex data flow. Once we see a namespace, we know we have to return the builder directly as an ImmutableArray of namespaces or types.
: ImmutableArray<TNamespaceOrTypeSymbol>.CastUp(builder.ToDowncastedImmutable<TNamedTypeSymbol>()); | ||
|
||
builder.Free(); | ||
return ImmutableArray<TNamespaceOrTypeSymbol>.CastUp(builder.ToDowncastedImmutableAndFree<TNamedTypeSymbol>()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if we get to end of the loop, we know we didn't have any namespaes, so no need to check any variablie and can just return teh downcasted values.
|
||
var builder = value as ArrayBuilder<TNamespaceOrTypeSymbol>; | ||
if (builder != null) | ||
static ImmutableArray<TNamespaceOrTypeSymbol> createMembers(object value) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
moving into local function eliminates complex control flow and tracking of variables. high level algorithm just walks the dictionary, transforming directly into a new dictionary.
{ | ||
ImmutableArray<TNamespaceOrTypeSymbol> members = kvp.Value; | ||
foreach (var (name, members) in map) | ||
dictionary.Add(name, getOrCreateNamedTypes(members)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
similarly, top level algorithm is just a walk on the dictionary, producing a new dictionary by transforming the values. I was considering a helper that both methods could call, but i was ok just inlining the foreaches in each. lmk if you'd prefer unification given the closeknit nature of these two methods.
|
||
bool hasType = false; | ||
bool hasNamespace = false; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no need for any tracking flags, or having to deal with any of the combinations of false/true, true/false, true/true (false/false can't happen as the value is always present and has at least one element it represents)
// See if creator 'map' put a downcasted ImmutableArray<TNamedTypeSymbol> in it. If so, we can just directly | ||
// downcast to that and trivially reuse it. If not, that means the array must have contained at least one | ||
// TNamespaceSymbol and we'll need to filter that out. | ||
var membersAsNamedTypes = members.As<TNamedTypeSymbol>(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we know that if we only had named types then CreateNameToMembersMap already put in a downcasted IA, so we can just directly try to move to that. no need for walking the arrays again.
} | ||
|
||
members = hasNamespaces | ||
? builder.ToImmutable() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ToImmutable is strictly worse than ToImmutableAndFree. The latter knows hte builder is being freed, so it can directly move the internal array into the final ImmutableArray (if the counts match). The former always has to copy for teh non-zero element case, which is unnecessary when a move is possible.
var result = ToDowncastedImmutable<U>(); | ||
this.Free(); | ||
return result; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i don't feel strongly about having this extension. would be ok inlining it. But it fits the pattern of how we use ArrayBuilders for the other ops, so i kept this in sync with those.
This is ready for review. |
It looks like this type parameter is no longer used in any meaningful way. In reply to: 1527577621 In reply to: 1527577621 Refers to: src/Compilers/Core/Portable/Collections/ImmutableArrayExtensions.cs:947 in f51fea2. [](commit_id = f51fea2, deletion_comment = False) |
Done with review pass (commit 2) |
There was no response to this comment In reply to: 1527577621 Refers to: src/Compilers/Core/Portable/Collections/ImmutableArrayExtensions.cs:947 in f51fea2. [](commit_id = f51fea2, deletion_comment = False) |
Odd. These comments don't appear to be in the source code. Something seems weird there. I was able to map this back though to the code you were asking about. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM (commit 9)
@RikkiGibson ptal :) |
: ImmutableArray<TNamespaceOrTypeSymbol>.CastUp(builder.ToDowncastedImmutable<TNamedTypeSymbol>()); | ||
|
||
builder.Free(); | ||
return ImmutableArray<TNamespaceOrTypeSymbol>.CastUp(builder.ToDowncastedImmutableAndFree<TNamedTypeSymbol>()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
answered offline.
* upstream/main: (2060 commits) implement code folding for anonymous objects Cleanup/perf in creating member maps. (dotnet#67997) Address feedback, clean the use of ILegacyGlobalOptionsWorkspaceService Update Publish.json Semantic snippets: Add inline statement snippets (dotnet#67819) Update VSSDK Build tools version Update doc comment Address feedback Move declaration near reference Address feedback Avoid stack overflow due to deep recursion on long chain of calls. (dotnet#67913) Check ILegacyGlobalOptionsWorkspaceService is null test scout queue add test update editor "Where" clause typo fix (dotnet#68002) Use `Keyword` helper method instead of hardcoding keyword help terms Move the SyntaxTree and SemanticModel action based analyzers to respect context.FilterSpan EnC refactoring: Align wrappers with contracts better (dotnet#67967) Include EA.RazorCompiler in source build (dotnet#67996) ...
Fixes #67990
Fixes #67991