如何 Nullable.GetUnderlyingType 而不会遇到可能的空引用问题
How to Nullable.GetUnderlyingType without hitting possible null reference issues
我正在尝试对旧库进行现代化改造以支持可为 null 的引用类型。
事实证明这一点很有挑战性。我想获取对象的类型。如果它是可空类型,那么我想要基础类型..
Type optionalType = //(a type that could be anything, including nullable types.)
if (optionalType.IsGenericType && optionalType.GetGenericTypeDefinition().Equals(typeof(Nullable<>)))
{
optionalType = Nullable.GetUnderlyingType(optionalType);
}
这并不令人满意,因为如果您传递一个不可为 null 的参数,GetUnderlyingType
将 return null。编译器显示错误 CS8600: Converting null literal or possible null value to non-nullable type.
但我已经对此有所防范。
有没有更好的方法,或者我必须在 optionalType
上允许空值?
如果您查看 Nullable.GetUnderlyingType
的源代码,您会发现它执行的检查与您正在执行的检查相同。事实上它做得更多:
public static Type GetUnderlyingType(Type nullableType) {
if((object)nullableType == null) {
throw new ArgumentNullException("nullableType");
}
Contract.EndContractBlock();
Type result = null;
if( nullableType.IsGenericType && !nullableType.IsGenericTypeDefinition) {
// instantiated generic type only
Type genericType = nullableType.GetGenericTypeDefinition();
if( Object.ReferenceEquals(genericType, typeof(Nullable<>))) {
result = nullableType.GetGenericArguments()[0];
}
}
return result;
}
正如@madreflection 所说,您可以用简单的方式替换整个代码块:
optionalType = Nullable.GetUnderlyingType(optionalType) ?? optionalType;
我正在尝试对旧库进行现代化改造以支持可为 null 的引用类型。
事实证明这一点很有挑战性。我想获取对象的类型。如果它是可空类型,那么我想要基础类型..
Type optionalType = //(a type that could be anything, including nullable types.)
if (optionalType.IsGenericType && optionalType.GetGenericTypeDefinition().Equals(typeof(Nullable<>)))
{
optionalType = Nullable.GetUnderlyingType(optionalType);
}
这并不令人满意,因为如果您传递一个不可为 null 的参数,GetUnderlyingType
将 return null。编译器显示错误 CS8600: Converting null literal or possible null value to non-nullable type.
但我已经对此有所防范。
有没有更好的方法,或者我必须在 optionalType
上允许空值?
如果您查看 Nullable.GetUnderlyingType
的源代码,您会发现它执行的检查与您正在执行的检查相同。事实上它做得更多:
public static Type GetUnderlyingType(Type nullableType) {
if((object)nullableType == null) {
throw new ArgumentNullException("nullableType");
}
Contract.EndContractBlock();
Type result = null;
if( nullableType.IsGenericType && !nullableType.IsGenericTypeDefinition) {
// instantiated generic type only
Type genericType = nullableType.GetGenericTypeDefinition();
if( Object.ReferenceEquals(genericType, typeof(Nullable<>))) {
result = nullableType.GetGenericArguments()[0];
}
}
return result;
}
正如@madreflection 所说,您可以用简单的方式替换整个代码块:
optionalType = Nullable.GetUnderlyingType(optionalType) ?? optionalType;