Udostępnij za pośrednictwem


Ulepszenia naturalnego typu dla grup metod

Notatka

Ten artykuł jest specyfikacją funkcji. Specyfikacja służy jako dokument projektowy dla funkcji. Zawiera proponowane zmiany specyfikacji wraz z informacjami wymaganymi podczas projektowania i opracowywania funkcji. Te artykuły są publikowane do momentu sfinalizowania proponowanych zmian specyfikacji i włączenia ich do obecnej specyfikacji ECMA.

Mogą wystąpić pewne rozbieżności między specyfikacją funkcji a ukończoną implementacją. Te różnice są przechwytywane w odpowiednich spotkania projektowego języka (LDM).

Więcej informacji na temat procesu wdrażania specyfikacji funkcji można znaleźć w standardzie języka C# w artykule dotyczącym specyfikacji .

Problem związany z mistrzostwami: https://github.com/dotnet/csharplang/issues/7429

Streszczenie

Ten wniosek uściśli określenie naturalnego typu grupy metod na kilka sposobów:

  1. Rozważ metody kandydatów według kolejnych zakresów: najpierw metody wystąpień, a następnie kolejne zakresy metod rozszerzeń.
  2. Odrzucaj kandydatów, którzy nie mają szans na sukces, aby nie zakłócali procesu ustalania jednoznacznego podpisu.
    • Przycinaj ogólne metody instancji, gdy nie podano argumentów typu (var x = M;)
    • Przycinaj ogólne metody rozszerzeń w oparciu o zdolność do zmniejszenia rozszerzenia oraz ograniczenia.

Kontekst dotyczący naturalnego typu grupy metod

W języku C# 10 grupy metod zyskały słaby typ naturalny.
Ten typ jest "słabym typem" w tym sensie, że wchodzi w grę tylko wtedy, gdy grupa metod nie jest związana z typem docelowym (tj. nie odgrywa żadnej roli w System.Action a = MethodGroup;).
Ten słaby typ naturalny umożliwia scenariusze, takie jak var x = MethodGroup;.

Dla odniesienia: https://github.com/dotnet/csharplang/blob/main/proposals/csharp-10.0/lambda-improvements.md#natural-function-type

Grupa metod ma typ naturalny, jeśli wszystkie metody kandydujące w grupie metod mają wspólną sygnaturę. (Jeśli grupa metod może zawierać metody rozszerzenia, kandydaci obejmują typ, który je zawiera i wszystkie zakresy metod rozszerzenia).

W praktyce oznacza to, że:

  1. Skonstruuj zestaw wszystkich metod kandydatów:
  • metody dla odpowiedniego typu znajdują się w zestawie, jeśli są statyczne, a odbiornik jest typem, lub jeśli są niestatyczne, a odbiornik jest wartością
  • metody rozszerzenia (we wszystkich zakresach), które można zmniejszyć, znajdują się w zestawie
  1. Jeśli podpisy wszystkich kandydatów nie są zgodne, grupa metod nie ma typu naturalnego
  2. Jeśli wartość arity wynikowego podpisu nie jest zgodna z liczbą podanych argumentów typu, grupa metod nie ma typu naturalnego
  3. W przeciwnym razie wynikowy podpis jest używany jako typ naturalny

Propozycja

Zasadą jest przechodzić przez każdy zakres i odrzucać kandydatów, o których wiemy, że nie mogą się powieść, tak szybko, jak to możliwe (ta sama zasada używana w rozwiązywaniu przeciążeń).

  1. Dla każdego zakresu tworzymy zestaw wszystkich kandydackich metod.
  • dla początkowego zakresu metody dla odpowiedniego typu z arnością pasującą do podanych argumentów typu i spełniające ograniczenia z podanymi argumentami typu należą do zestawu, jeśli są statyczne i odbiornik jest typem, lub jeśli są niestatyczne i odbiornik jest wartością
  • dla kolejnych zakresów, metody rozszerzenia w tych zakresach, które mogą zostać zastąpione podanymi argumentami typu i uproszczone przy użyciu wartości odbiornika pod warunkiem, że spełniają ograniczenia, znajdują się w zestawie
  1. Jeśli nie mamy kandydatów w danym zakresie, przejdź do następnego zakresu.
  2. Jeśli podpisy wszystkich kandydatów nie są zgodne, grupa metod nie ma typu naturalnego
  3. W przeciwnym razie wynikowy podpis jest używany jako typ naturalny
  4. Jeśli zakresy są wyczerpane, grupa metod nie ma typu naturalnego

Odnosi się do propozycji zakresu według zakresu: https://github.com/dotnet/csharplang/issues/7364 Odnosi się do propozycji w celu lepszego obsługi ogólnych metod rozszerzeń: https://github.com/dotnet/roslyn/issues/69222