0

C# 允许创建如下属性:

public string SomeRandomText
{
    get; set;
}

框架处理此属性的支持变量的创建。我怎样才能拥有这样的财产并且仍然有更改通知?

这在实现 INotifyPropertyChanged 的​​类中是否允许?

public string SomeRandomTextBeingNotified
{
    get;
    set
    {
        NotifyPropertyChanged("SomeRandomTextBeingNotified");
    }
}
4

5 回答 5

3

尝试使用它时不能使用自动属性。您需要创建一个后备存储:

private string _someRandomText;
public string SomeRandomText {
    get { return _someRandomText; }
    set 
    {
        _someRandomText = value;
        NotifyPropertyChanged("SomeRandomText");
    }
}
于 2012-11-27T06:37:21.377 回答
1

为了使代码看起来更干净,您可以使用 INotifyPropertyChanged 的​​属性。

使用 Property-Attribute 轻松使用 INotifyPropertyChanged

看看这个Use of Attributes... INotifyPropertyChanged

于 2012-11-27T06:42:43.867 回答
1

实际上你可以,但你基本上需要在 C# 编译器后更改字节码。

这听起来可能需要做很多工作,但这是 PostSharp 所包含的更简单的后处理步骤之一。

http://www.sharpcrafters.com/solutions/notifypropertychanged

http://www.sharpcrafters.com/blog/post/Recording-Automate-INotifyPropertyChanged-with-Karol-Waledzik-from-Internetium.aspx

还有更多功能可用;)

否则请注意

enter code here在此处输入代码`NotifyPropertyChanged("SomeRandomTextBeingNotified");

是坏代码。我在一个字段更新方法中完成所有这些:

set 
{
    OnUpateField (ref _someRandomText, value);
}

update 方法完成所有工作 - 检查是否相等(您不想在新值 = 旧值时触发),然后根据需要触发更新。它通过编译器自动设置的调用方法第三个参数获取属性名称。替代方法是使用 LINQ 语句(ref someRandomText, value, this->SomeRandomText)。我永远不会喜欢在重构时不会重命名的字符串;)

于 2012-11-27T06:43:13.490 回答
1

如果您没有基类,那么像这样的东西很容易而且非常灵活:

public class NotificationObject : INotifyPropertChanged
{
    private readonly Dictionary<string, object> Properties = new Dictionary<string, object>();

    public event PropertyChangedEventHandler PropertyChanged;

    protected TType Get<TType>(string propertyName)
    {
        object value;
        return Properties.TryGetValue(propertyName, out value) ? (TType)value : default(TType);
    }

    protected void Set<TType>(TType value, string propertyName, params string[] dependantPropertyNames)
    {
        Properties[propertyName] = value;
        OnPropertyChanged(propertyName);
        if (dependantPropertyNames != null)
        {
            foreach (string dependantPropertyName in dependantPropertyNames)
            {
                OnPropertyChanged(dependantPropertyName);
            }
        }
    }

    protected void OnPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArts(propertyName));
        }
    }
}

这可以像这样使用:

public SomeObjectThatNeedsToNotifySomething : NotificationObject
{
    public int SomeValue
    {
        get { return Get<int>("SomeValue"); }
        set { Set<int>(value, "SomeValue", "SomeAggregateValue"); }
    }

    public int SomeOtherValue
    {
        get { return Get<int>("SomeOtherValue"); }
        set { Set<int>(value, "SomeOtherValue", "SomeAggregateValue"); }
    }

    public int SomeAggregateValue
    {
        get { return SomeValue + SomeOtherValue; }
    }
}

如果你已经有一个基类并且只需要实现 INotifyPropertyChanged 接口,@Rob 是正确的,提供一个支持字段并触发事件。

于 2012-11-27T06:49:33.467 回答
1

没有半自动属性之类的东西。尽管如此,有很多方法可以实现 INotifyPropertyChanged,它们不需要繁琐的命令式代码。

1)前面提到过:PostSharp,一个面向切面的商业项目。

2) 创建 Castle DynamicProxy 解决方案。可以在这里找到样本,实际上还有很多其他样本。

在通用解决方案上投入一些时间是值得的,样板代码会在一段时间后变得令人烦恼并且容易出错。

于 2012-11-27T07:24:33.510 回答