【发布时间】:2019-07-31 12:19:50
【问题描述】:
我需要能够监控大量对象的变化。几乎在任何情况下,我都可以使用INotifyPropertyChanged 并收工。然而,我的情况并没有那么简单。我的项目的目标是创建一个可以插入、监控和访问任何对象的模拟。
插入是通过使用 Fluent API 的反射完成的,该 API 指定要包含在模拟环境中的属性和字段。它看起来像这样:
public void DeclareVariables( IVariableBuilder builder )
{
builder.Include( x => x.PropertyA );
builder.Include( x => x.FieldA );
}
然后将属性和字段包装在 Variable 类中并存储在 Environment 类中。
public class Variable<T> : IVariable
{
private FieldInfo _field; // Properties are turned into FieldInfo via k__BackingField
private object _obj;
public string Id
{
get => $"{_obj.GetType}-{_field.Name}";
}
public T Value
{
get => _field.GetValue( _obj );
}
}
public class Environment
{
private Dictionary<string, IVariable> _variables;
}
这会正确存储对我尝试包含的所有字段和属性的引用。 但是,我希望能够监控所有这些更改,并且大多数包含的字段都是闭源类或原语,两者都没有实现 INotifyPropertyChanged` 或无法派生。
我来自 JavaScript 背景,您可以通过创建一个可以覆盖属性 getter 和 setter 的对象代理来完成此操作,并且由于 JavaScript 是鸭子类型的,您只需将实际的对象实例就地替换为代理.
有没有办法在 C# 中做同样的事情?我想 C# 的类型安全规则不允许这样的做法,尤其是对于原语。然而,据我所知,监控这些类的唯一方法是以某种方式拦截正在设置值的操作。
【问题讨论】:
标签: c# metaprogramming proxy-pattern