private static ImmutableArray <SerializableImportCompletionItem> ConvertSymbolsToCompletionItems(ImmutableArray <IMethodSymbol> extentsionMethodSymbols, CancellationToken cancellationToken) { using var _1 = PooledDictionary <INamespaceSymbol, string> .GetInstance(out var namespaceNameCache); using var _2 = PooledDictionary <(string containingNamespace, string methodName, bool isGeneric), (IMethodSymbol bestSymbol, int overloadCount)> .GetInstance(out var overloadMap); // Aggregate overloads foreach (var symbol in extentsionMethodSymbols) { IMethodSymbol bestSymbol; int overloadCount; var containingNamespacename = GetFullyQualifiedNamespaceName(symbol.ContainingNamespace, namespaceNameCache); var overloadKey = (containingNamespacename, symbol.Name, isGeneric : symbol.Arity > 0); // Select the overload with minimum number of parameters to display if (overloadMap.TryGetValue(overloadKey, out var currentValue)) { bestSymbol = currentValue.bestSymbol.Parameters.Length > symbol.Parameters.Length ? symbol : currentValue.bestSymbol; overloadCount = currentValue.overloadCount + 1; } else { bestSymbol = symbol; overloadCount = 1; } overloadMap[overloadKey] = (bestSymbol, overloadCount); } // Then convert symbols into completion items using var _3 = ArrayBuilder <SerializableImportCompletionItem> .GetInstance(out var itemsBuilder); foreach (var((containingNamespace, _, _), (bestSymbol, overloadCount)) in overloadMap) { // To display the count of of additional overloads, we need to substract total by 1. var item = new SerializableImportCompletionItem( SymbolKey.CreateString(bestSymbol, cancellationToken), bestSymbol.Name, bestSymbol.Arity, bestSymbol.GetGlyph(), containingNamespace, additionalOverloadCount: overloadCount - 1); itemsBuilder.Add(item); } return(itemsBuilder.ToImmutable()); }
private static ImmutableArray <SerializableImportCompletionItem> ConvertSymbolsToCompletionItems( Compilation compilation, ImmutableArray <IMethodSymbol> extentsionMethodSymbols, ImmutableArray <ITypeSymbol> targetTypeSymbols, CancellationToken cancellationToken) { Dictionary <ITypeSymbol, bool> typeConvertibilityCache = new(); using var _1 = PooledDictionary <INamespaceSymbol, string> .GetInstance(out var namespaceNameCache); using var _2 = PooledDictionary <(string containingNamespace, string methodName, bool isGeneric), (IMethodSymbol bestSymbol, int overloadCount, bool includeInTargetTypedCompletion)> .GetInstance(out var overloadMap); // Aggregate overloads foreach (var symbol in extentsionMethodSymbols) { cancellationToken.ThrowIfCancellationRequested(); IMethodSymbol bestSymbol; int overloadCount; var includeInTargetTypedCompletion = ShouldIncludeInTargetTypedCompletion(compilation, symbol, targetTypeSymbols, typeConvertibilityCache); var containingNamespacename = GetFullyQualifiedNamespaceName(symbol.ContainingNamespace, namespaceNameCache); var overloadKey = (containingNamespacename, symbol.Name, isGeneric : symbol.Arity > 0); // Select the overload convertible to any targeted type (if any) and with minimum number of parameters to display if (overloadMap.TryGetValue(overloadKey, out var currentValue)) { if (currentValue.includeInTargetTypedCompletion == includeInTargetTypedCompletion) { bestSymbol = currentValue.bestSymbol.Parameters.Length > symbol.Parameters.Length ? symbol : currentValue.bestSymbol; } else if (currentValue.includeInTargetTypedCompletion) { bestSymbol = currentValue.bestSymbol; } else { bestSymbol = symbol; } overloadCount = currentValue.overloadCount + 1; includeInTargetTypedCompletion = includeInTargetTypedCompletion || currentValue.includeInTargetTypedCompletion; } else { bestSymbol = symbol; overloadCount = 1; } overloadMap[overloadKey] = (bestSymbol, overloadCount, includeInTargetTypedCompletion); } // Then convert symbols into completion items using var _3 = ArrayBuilder <SerializableImportCompletionItem> .GetInstance(out var itemsBuilder); foreach (var((containingNamespace, _, _), (bestSymbol, overloadCount, includeInTargetTypedCompletion)) in overloadMap) { // To display the count of additional overloads, we need to subtract total by 1. var item = new SerializableImportCompletionItem( SymbolKey.CreateString(bestSymbol, cancellationToken), bestSymbol.Name, bestSymbol.Arity, bestSymbol.GetGlyph(), containingNamespace, additionalOverloadCount: overloadCount - 1, includeInTargetTypedCompletion); itemsBuilder.Add(item); } return(itemsBuilder.ToImmutable()); }