Примечание
Для доступа к этой странице требуется авторизация. Вы можете попробовать войти или изменить каталоги.
Для доступа к этой странице требуется авторизация. Вы можете попробовать изменить каталоги.
Универсальный метод — это метод, объявленный с параметрами типа, как показано ниже.
static void Swap<T>(ref T lhs, ref T rhs)
{
T temp;
temp = lhs;
lhs = rhs;
rhs = temp;
}
В следующем примере кода показан один из способов вызова метода с помощью int
аргумента типа:
public static void TestSwap()
{
int a = 1;
int b = 2;
Swap<int>(ref a, ref b);
System.Console.WriteLine(a + " " + b);
}
Вы также можете опустить аргумент типа, и компилятор выдаст его. Следующий вызов Swap
эквивалентен предыдущему вызову:
Swap(ref a, ref b);
Те же правила вывода типов применяются к статическим методам и методам экземпляра. Компилятор может определить параметры типа на основе передаваемых аргументов метода; Он не может выводить параметры типа только из ограничения или возвращаемого значения. Поэтому вывод типов не работает с методами, не имеющими параметров. Вывод типов происходит во время компиляции, прежде чем компилятор пытается разрешить перегруженные подписи метода. Компилятор применяет логику вывода типов ко всем универсальным методам, которые имеют одно и то же имя. На шаге разрешения перегрузки компилятор включает только те универсальные методы, на которых выполнен вывод типов.
В универсальном классе не универсальные методы могут получить доступ к параметрам типа уровня класса следующим образом:
class SampleClass<T>
{
void Swap(ref T lhs, ref T rhs) { }
}
Если вы определяете универсальный метод, который принимает те же параметры типа, что и содержащий класс, компилятор создает предупреждение CS0693 , так как в области метода аргумент, предоставленный внутренним T
, скрывает аргумент, предоставленный для внешнего T
. Если требуется гибкость вызова метода универсального класса с аргументами типа, отличными от аргументов типа, предоставленных при создании экземпляра класса, рассмотрите возможность предоставления другого идентификатора параметра типа метода, как показано в GenericList2<T>
следующем примере.
class GenericList<T>
{
// CS0693.
void SampleMethod<T>() { }
}
class GenericList2<T>
{
// No warning.
void SampleMethod<U>() { }
}
Используйте ограничения для включения более специализированных операций с параметрами типа в методах. Эта версия Swap<T>
, теперь именованной SwapIfGreater<T>
, может использоваться только с аргументами типа, реализующими IComparable<T>.
void SwapIfGreater<T>(ref T lhs, ref T rhs) where T : System.IComparable<T>
{
T temp;
if (lhs.CompareTo(rhs) > 0)
{
temp = lhs;
lhs = rhs;
rhs = temp;
}
}
Универсальные методы могут быть перегружены по нескольким параметрам типа. Например, следующие методы могут находиться в одном классе:
void DoWork() { }
void DoWork<T>() { }
void DoWork<T, U>() { }
Вы также можете использовать параметр типа в качестве возвращаемого типа метода. В следующем примере кода показан метод, возвращающий массив типа T
:
T[] Swap<T>(T a, T b)
{
return [b, a];
}
Спецификация языка C#
Дополнительные сведения см. в спецификации языка C#.