我知道这可能听起来有点奇怪,但我想将T?
的对象强制转换为int?
。我想要这个的原因是T
总是一个枚举,我也知道这个枚举可以转换为int。我为枚举创建了一个通用包装类,并发现this "solution"将泛型类型约束为枚举类型。
我的代码目前看起来像这样:
public class EnumWrapper<T>
where T : struct, IConvertible
{
public EnumWrapper()
{
if (!typeof(T).IsEnum)
{
throw new ArgumentException("T must be an enumerated type");
}
}
public T? Enum { get; set; }
public int? EnumValue => (int?)Enum; // this won't compile
...
}
我知道在转换为值类型((int?)(object)Enum
)之前强制转换为对象会欺骗编译器,但这也适用于此吗?我怀疑可以为空的人干扰了这一点。
所以我的问题是:实现这种通用行为的最佳方法是什么?
答案 0 :(得分:2)
由于T
为IConvertible
,您可以使用ToInt32()
方法避免投射和装箱:
public int? EnumValue => this.Enum?.ToInt32(CultureInfo.CurrentCulture.NumberFormat);
如果缺少实际值,this.Enum?
将确保返回null
。
此外,由于我们正在尝试保留已包装的枚举的值类型语义,因此您需要将EnumWrapper
从class
更改为struct
并且使用扩展方法轻松包装值:
public struct EnumWrapper<T> where T : struct, IConvertible
{
public T? Enum { get; set; }
public int? EnumValue => this.Enum?.ToInt32(CultureInfo.CurrentCulture.NumberFormat);
}
public static class EnumWrapperExtension
{
public static EnumWrapper<T> Wrap<T>(this T data) where T : struct, IConvertible
{
if (!typeof(T).IsEnum)
throw new ArgumentException("T must be an enumerated type");
return new EnumWrapper<T> { Enum = data };
}
}
用法:
public enum Color
{
Red = 1,
Green = 2,
}
var color = Color.Green;
var colorAsInt = color.Wrap().EnumValue;
请参阅MSDN