C# 使用 INotifyPropertyChange 压缩 class 中的冗余代码

C# condense redundant code in class with INotifyPropertyChange

过去几天我一直在阅读一些关于继承 classes 和创建基础 classes 的文章,我经常在我编写的工具中这样做。但是,我专门研究了减少冗余代码的方法,这些冗余代码通常写在我的 classes 中,其中包含 INotifyPropertyChange。通常我的 classes 看起来像这样,继承了 NotifyBase 的基础 class。然而,我在这里看到人们在各种脚本中将一些 Get 和 Set 代码移动到基础 class 中。我想知道做这个的时候要注意什么?这是不好的做法还是好的做法?我提供的示例写得正确吗?

一个好处是 Get 和 Set 在新设置中继承 NotifyBase 的 classes 中要简单得多。

当前设置示例

文件项Class

using System.IO;

namespace WpfApplication1
{
    public class FileItem : NotifyBase
    {
        private string _fullPath;
        public string FullPath
        {
            get { return this._fullPath; }
            set
            {
                this._fullPath = value;
                this.NotifyPropertyChanged("FullPath");
            }
        }
    }
}

Base Class 'NotifyBase'

using System.Collections.Generic;
using System.ComponentModel;
using System.Runtime.CompilerServices;

namespace WpfApplication1
{
    public class NotifyBase : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        public void NotifyPropertyChanged([CallerMemberName] string propertyName = null)
        {
            PropertyChangedEventHandler handler = PropertyChanged;
            if (handler != null)
            {
                handler(this, new PropertyChangedEventArgs(propertyName));
            }
        }
    }
}

可能的新设置

文件项Class

using System.IO;

namespace WpfApplication1
{
    public class FileItem : NotifyBase
    {
        public string FullPath
        {
            get { return Get<string>(); }
            set { Set(value); }
        }
    }
}

Base Class 'NotifyBase'

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Runtime.CompilerServices;

namespace Varo.Helper
{
    public class NotifyBase : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        public void NotifyPropertyChanged([CallerMemberName] string propertyName = null)
        {
            PropertyChangedEventHandler handler = PropertyChanged;
            if (handler != null)
            {
                handler(this, new PropertyChangedEventArgs(propertyName));
            }
        }

        private readonly Dictionary<string, object> _propertyValues;

        protected NotifyBase()
        {
           _propertyValues = new Dictionary<string, object>();
        }

        protected void Set<T>(T value, [CallerMemberName] string name = "")
        {
           if (_propertyValues.ContainsKey(name))
           {

               _propertyValues[name] = value;
               NotifyPropertyChanged(name);

           }
           else
           {
               _propertyValues.Add(name, value);
               NotifyPropertyChanged(name);
           }
        }

        protected T Get<T>([CallerMemberName] string name = "")
        {
           if (_propertyValues.ContainsKey(name))
           {
               return (T)_propertyValues[name];
           }
           return default(T);
        }
    }
}

检查 PropertyChanged.Fody NuGet

在编译时编织 .NET 程序集,因此属性声明为

 public int Property { get; set; }

编译为

 private int property;
 public int Property 
 {
      get 
      {
        return property;
      }
      set
      {
        if(property != value)
        {
             property = value;
             if (this.PropertyChanged!= null) PropertyChanged(this, new PropertyChangedEventArgs("Property");
        }
      }
 }