Создает ли общий метод С#, который допускает (нулевой) тип значения и ссылочный тип?
Я хочу создать простой метод, который принимает значения типа значения и ссылочного типа, т.е. int является значением, а строка является ссылкой.
Итак, я начинаю с:
public bool areBothNotNull<T>(T? p1, T? p2)
{
return (p1.HasValue && p2.HasValue);
}
Итак, я хочу иметь возможность использовать его вот так:
var r1 = areBothNotNull<int>(3, 4); // will be true
var r2 = areBothNotNull<int>(3, null); // will be false
var r3 = areBothNotNull<string>("three", "four"); // will be true
var r4 = areBothNotNull<string>(null, "four"); // will be false
Но первая проблема, с которой я сталкиваюсь, -
Тип "T" должен быть невообразимым типом значения, чтобы использовать его как параметр "T" в родовом типе или методе "System.Nullable",
Чтобы продолжить, добавьте ограничение struct к моему методу
public bool areBothNotNull<T>(T? p1, T? p2) where T : struct
Но теперь метод не будет принимать строковые вызовы и даст мне эту ошибку:
Тип "string" должен быть невообразимым типом значения, чтобы использовать его как параметр "T" в родовом типе или методе.
Возможно ли это? Или почему мы не можем этого сделать?
Ответы
Ответ 1
Ваша проблема в том, что вы хотите, чтобы общие ограничения типа противоречили друг другу:
-
Nullable<T>
работает только с типами значений
- Типы ссылок не являются типами значений
Таким образом, вам нужно будет иметь две перегрузки для работы вашего кода:
public static bool areBothNotNull<T>(T? p1, T? p2) where T : struct
{
return (p1.HasValue && p2.HasValue);
}
public static bool areBothNotNull<T>(T p1, T p2)
{
return (p1 != null && p2 != null);
}
Тем не менее, следующая строка никогда не будет компилироваться:
var r3 = areBothNotNull<string>(3, 4);
Здесь существует конфликт, в котором аргумент generic type указывает, что параметры имеют тип string
, но код пытается передать int
.