C#3.0自动属性-是否可以添加自定义行为?
时间:2020-03-06 14:33:05 来源:igfitidea点击:
我想知道是否有任何方法可以向auto属性的get / set方法中添加自定义行为。
我可以想到的一个明显的例子是,希望每个set属性方法都调用任何System.ComponentModel.INotifyPropertyChanged实现的一部分PropertyChanged事件处理程序。这将使一个类具有许多可以观察到的属性,其中每个属性都是使用自动属性语法定义的。
基本上,我想知道是否有任何类似于具有类范围的get / set模板或者post get / set挂钩。
(我知道可以通过稍微冗长的方式轻松实现相同的最终功能,而我只是讨厌重复模式)
解决方案
不,我们必须对自定义行为使用"传统"属性定义。
如果我们要在开发过程中重复这种行为,则可以为特殊类型的属性创建一个自定义代码段。
不,我们不能:auto属性是显式访问私有字段的快捷方式。例如
public string Name { get; set;}
是通往的捷径
private string _name; public string Name { get { return _name; } set { _name = value; } };
如果要放置自定义逻辑,则必须明确编写get和set。
我们可以考虑使用PostSharp编写setter的拦截器。它取决于LGPL和GPL,具体取决于我们使用的是哪一部分库。
我能想到的最接近的解决方案是使用辅助方法:
public void SetProperty<T>(string propertyName, ref T field, T value) { field = value; NotifyPropertyChanged(propertyName); } public Foo MyProperty { get { return _myProperty} set { SetProperty("MyProperty",ref _myProperty, value);} } Foo _myProperty;
查看PostSharp。这是一个AOP框架,通常会发出"这种代码模式我每天都费时费力,如何使其自动化?"。
我们可以使用PostSharp简化此操作(例如):
public Class1 DoSomething( Class2 first, string text, decimal number ) { if ( null == first ) { throw new ArgumentNullException( "first" ); } if ( string.IsNullOrEmpty( text ) ) { throw new ArgumentException( "Must be not null and longer than 0.", "text" ) ; } if ( number < 15.7m || number > 76.57m ) { throw new OutOfRangeArgumentException( "Minimum is 15.7 and maximum 76.57.", "number"); } return new Class1( first.GetSomething( text ), number + text.Lenght ); }
到
public Class1 DoSomething( [NotNull]Class2 first, [NotNullOrEmpty]string text, [InRange( 15.7, 76.57 )]decimal number ) { return new Class1( first.GetSomething( text ), number + text.Lenght ); }
但这并不是全部! :)