C#中如何通过派生类类型访问泛型基类的静态字段?
问题描述
基类代码:
namespace Business; public abstract class Business<ReadModel, WriteModel> : ReadBusiness<ReadModel> where ReadModel : class, IEntity, new() where WriteModel : class, IEntity, new() { protected abstract Write<WriteModel> Write { get; } public static List<Action<WriteModel>> PreCreationAugmenters = new List<Action<WriteModel>>(); public static List<Action<WriteModel>> PostCreationAugmenters = new List<Action<WriteModel>>(); public static List<Action<WriteModel>> PreUpdateAugmenters = new List<Action<WriteModel>>(); }
派生类代码:
namespace Taxonomy; public class TagBusiness : Business<TagView, Tag> { }
尝试通过typeof(TagBusiness)访问基类的PostCreationAugmenters静态字段,以下代码均返回null:
typeof(TagBusiness).GetProperty("PostCreationAugmenters", BindingFlags.Static); // null typeof(TagBusiness).GetField("PostCreationAugmenters", BindingFlags.Static); //null typeof(TagBusiness).BaseType.GetProperty("PostCreationAugmenters"); // null
需要获取该列表并添加增强器,请问哪里操作错误了?
解决方案
问题出在两个核心点:
PostCreationAugmenters是字段不是属性,所以GetProperty必然返回null;- 使用
GetField时仅传入BindingFlags.Static参数不全,同时泛型基类的静态字段属于构造后的具体泛型类型,需要正确指定绑定标志并定位到对应类型。
正确的实现代码如下:
// 1. 获取TagBusiness对应的泛型基类实例(Business<TagView, Tag>) var genericBaseType = typeof(TagBusiness).BaseType; // 2. 指定Public+Static的绑定标志,获取目标字段 var field = genericBaseType.GetField("PostCreationAugmenters", BindingFlags.Public | BindingFlags.Static); // 3. 获取字段值(静态字段无需实例,传null即可) var augmentersList = field.GetValue(null) as List<Action<Tag>>; // 4. 添加自定义增强逻辑 augmentersList?.Add(tag => { // 这里写你的增强代码,比如给Tag对象设置默认值 });
或者直接通过构造后的泛型类型获取,写法更简洁:
var field = typeof(Business<TagView, Tag>).GetField("PostCreationAugmenters", BindingFlags.Public | BindingFlags.Static); var augmentersList = field.GetValue(null) as List<Action<Tag>>; augmentersList?.Add(...);
错误原因说明
- BindingFlags参数缺失:只传
BindingFlags.Static时,默认会匹配非公共的静态成员,而你的字段是public修饰的,必须同时加上BindingFlags.Public才能找到目标字段。 - 泛型类型的静态字段归属:泛型基类的静态字段属于构造后的具体泛型类型(比如
Business<TagView, Tag>),而非未构造的泛型定义(Business<,>),所以通过TagBusiness.BaseType拿到的构造后类型,配合正确的绑定标志就能成功获取字段。
内容的提问来源于stack exchange,提问作者Sharif Rezvani
相关产品推荐
相关产品推荐

