随着 .NET 4.5.3 的出现,WPF 开发人员现在可以通过三种(或更多)方式通知 INotifyPropertyChanged
Interface的属性变化。基本上,我的问题是从 .NET 4.5 开始引入的两种方法中,哪种方法更有效地通知属性更改,以及在 WPF 中使用这两种方法是否有任何好处?
背景
对于那些不太熟悉这个主题的人,这里是主要的三种方法。第一种是原始的、更容易出错的简单传递字符串的方法:
public string TestValue
{
get { return testValue; }
set { testValue = value; NotifyPropertyChanged("TestValue"); }
}
protected virtual void NotifyPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
第二种方法是.NET 4.5引入的; CallerMemberNameAttribute
:
public string TestValue
{
get { return testValue; }
set { testValue = value; NotifyPropertyChanged(); }
}
protected virtual void NotifyPropertyChanged([CallerMemberName]string propertyName = "")
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
第三种也是最新的方法是(或即将)作为 .NET 4.5.3 的一部分在 C#6.0 中引入的; nameof
Operator :
public string TestValue
{
get { return testValue; }
set { testValue = value; NotifyPropertyChanged(nameof(TestValue)); }
}
protected virtual void NotifyPropertyChanged(string propertyName)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
我自己的假设是,最初的、更容易出错的简单传递字符串的方法是最有效的,因为我只能想象其他两种方法使用某种形式的反射。但是,我真的很想知道其他两种方法中哪一种更有效,以及使用 CallerMemberNameAttribute
属性和 nameof
运算符之间是否真的有任何区别在 WPF 上下文中。
最佳答案
关于效率:直接使用字符串,CallerMemberNameAttribute
,nameof
都是完全一样的,因为字符串是编译器在编译时注入(inject)的。不涉及反射。
我们可以看到使用 TryRoslyn produces this for CallerMemberNameAttribute
:
public string TestValue
{
get { return this.testValue; }
set { this.testValue = value; this.NotifyPropertyChanged("TestValue"); }
}
protected virtual void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
{
if (this.PropertyChanged != null)
{
this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
public string TestValue
{
get { return this.testValue; }
set { this.testValue = value; this.NotifyPropertyChanged("TestValue"); }
}
protected virtual void NotifyPropertyChanged(string propertyName)
{
if (this.PropertyChanged != null)
{
this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
由于在运行时所有选项都只是一个字符串
,因此 WPF 上下文没有问题。
关于方便:CallerMemberNameAttribute
要求您有一个可选参数,而 nameof
不需要,但是 nameof
要求您指定属性,而 CallerMemberNameAttribute
没有。
我预测 nameof
会变得如此流行以致于使用它会简单得多。
关于c# - 使用 nameof 运算符而不是 CallerMemberNameAttribute 来通知 .NET 4.5.3 中的属性更改有什么好处吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28397256/