Вы пытаетесь указать нужные параметры типа в общем определении, что не сработает.Если вы хотите иметь версии метода, которые поддерживают (для второго параметра) объекты типа int, long, and T
, объявите 2 неуниверсальные перегрузки метода и одну универсальную.
void S(int a, int b)
void S(int a, long b)
void S<T>(int a, T b)
Разрешение перегрузки затем вызовет соответствующий метод на основе аргументов, сопоставляя неуниверсальные версии для точных совпадений на int
или long
(вы можете получитьуниверсальная версия даже с параметром int
или long
, если вы явно вызываете его с помощью параметра типа), в противном случае получается универсальная версия.
Примеры:
void S<T>(int a, T b)
{
Console.WriteLine("generic method");
}
void S(int a, int b)
{
Console.WriteLine("int overload");
}
void S(int a, long b)
{
Console.WriteLine("long overload");
}
...
S(10, 10);
S(10, (long)10);
S(10, 10L);
S(10, 10M);
S<int>(10, 10); // uses generic
S<long>(10, 10); // uses generic & implicit conversion
Редактировать: Чтобы подробнее остановиться на пункте, упомянутом кратко выше и далее в комментариях, соответствие для перегрузок int
и long
должно составлять точный. Все остальные аргументы приведут к выбору универсальной версии.Если у вас нет int , но требуется перегрузка int , вам необходимо явно преобразовать аргумент до или во время вызова метода.например: S(10, (int)myShort);
.
Аналогично, если у вас есть две версии метода C
void C(Mammal m) { }
void C<T>(T t) { }
с
class Tiger : Mammal { }
Вызов C(new Tiger())
приведет к использованию универсального метода,Если вы хотите перегрузку Mammal
для экземпляра Tiger
, вам нужна ссылка через базовый класс.Такие как
Mammal m = new Tiger();
C(m); // uses mammal overload
// or
Tiger t = new Tiger();
C((Mammal)t); // uses mammal overload