问题 关于IOC容器的有用性,获奖提交者提到,使用IOC容器,您可以采用此操作:

public class UglyCustomer : INotifyPropertyChanged
{
    private string _firstName;
    public string FirstName
    {
        get { return _firstName; }
        set
        {
            string oldValue = _firstName;
            _firstName = value;
            if(oldValue != value)
                OnPropertyChanged("FirstName");
        }
    }

    private string _lastName;
    public string LastName
    {
        get { return _lastName; }
        set
        {
            string oldValue = value;
            _lastName = value;
            if(oldValue != value)
                OnPropertyChanged("LastName");
        }
    }
}

为此:

var bindingFriendlyInstance = IoC.Resolve<Customer>(new NotifyPropertyChangedWrapper()); 

问题:

  • 哪个魔术IOC容器提供了这种优点?
  • 实施此功能的示例?
  • 有缺点吗?
  • 在具有复杂依赖性的项目中,当我尝试将数据绑定到这些对象时,我会哭泣吗?
有帮助吗?

解决方案

对于您的第二个代码段工作, NotifyPropertyChangedWrapper 当然必须使用反思(或 dynamic)生成一个提供与接口兼容的类 Customer 并实现自动属性通知。不应该有任何数据绑定问题,但是会有一些开销。

使用动态对象的简化实现可以看起来像这样:

public class NotifyPropertyChangedWrapper<T> 
    : DynamicObject, INotifyPropertyChanged
{
    private T _obj;

    public NotifyPropertyChangedWrapper(T obj)
    {
        _obj = obj;
    }

    public override bool TryGetMember(
        GetMemberBinder binder, out object result)
    {
        result = typeof(T).GetProperty(binder.Name).GetValue(_obj);
        return true;
    }

    // If you try to set a value of a property that is
    // not defined in the class, this method is called.
    public override bool TrySetMember(
        SetMemberBinder binder, object value)
    {
        typeof(T).GetProperty(binder.Name).SetValue(_obj, value);
        OnPropertyChanged(binder.Name);
        return true;
    }

    // Implement OnPropertyChanged...
}

显然,任何消耗这些对象之一的代码都会失去任何静态类型的安全性。另一个选项是生成一个与所包装类相同接口的类。网络上有很多示例。主要要求是您 Customer 要么必须是 interface 或者它需要其所有属性才能虚拟。

其他提示

要以通用的方式执行此操作(即为任何类实现InotifyPropertychanged的一件代码)使用代理。周围有很多实现 Castle.Dynamicproxy 或者 linfu 或者 统一. 。这些代理库在IOC容器中具有良好的支持,例如,DynamicProxy与Castle Windsor和Unity拦截(或所谓的任何内容)具有良好的集成,显然与Unity容器具有良好的集成。

我从未使用过,但是您可以使用它来创建这样的东西 后期.

如果您正在寻找用于自动生成可约束物体的特定解决方案,则应查看 属性汇总 (以前通知propertyweaver)。这将重写实现InotifyPropertychanged的类以包含通知代码。 GitHub页面上有一个示例。

我认为这比使用建议的IOC容器解决方案更加整洁。但是,它是一个特定于InotifyPropertychanged Binding的库,因此不适用于一般解决方案,就像您链接的问题中所讨论的那样。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top