如何让泛型抽象基类EnumClass<T>的静态Parse方法返回派生类实例
你可以通过奇异递归模板模式(CRTP) 为基类增加派生类类型的泛型参数,配合反射创建派生类实例,同时解决两个问题:
调整后的抽象基类实现
// 标记为抽象类 public abstract class EnumClass<T, TDerived> where T : Enum where TDerived : EnumClass<T, TDerived> { public T Value { get; } public string Name { get; } // 构造函数改为protected,只允许派生类调用 protected EnumClass(T enumValue) { Value = enumValue; Name = Enum.GetName(typeof(T), enumValue); } // 直接返回派生类类型 public static TDerived Parse(string name) { var enumValue = (T)Enum.Parse(typeof(T), name); // 反射调用派生类的构造函数创建实例,无需实例化抽象基类 return Activator.CreateInstance(typeof(TDerived), enumValue) as TDerived; } // 【可选优化】静态构造函数提前校验派生类构造合法性,避免运行时才报错 static EnumClass() { var constructor = typeof(TDerived).GetConstructor(new[] { typeof(T) }); if (constructor == null) { throw new InvalidOperationException($"派生类 {typeof(TDerived).Name} 必须实现接收 {typeof(T).Name} 类型参数的公共构造函数"); } } }
派生类改造示例
// 继承时传入派生类自身作为第二个泛型参数 public class AnimalTypes : EnumClass<AnimalTypesEnum, AnimalTypes>, IMyEnumInterface { public AnimalTypes(AnimalTypesEnum value) : base(value) { } } public enum AnimalTypesEnum { [Description("Cat")] CAT, [Description("Dog")] DOG, [Description("Horse")] HORSE, [Description("Bear")] BEAR }
调用效果
// 直接返回AnimalTypes类型,无需强制转换 AnimalTypes dog = AnimalTypes.Parse("DOG");
内容的提问来源于stack exchange,提问作者Maurdekye
相关产品推荐
相关产品推荐

