7

我对如何ObservableCollectionINotifyPropertyChanged工作感到困惑。

我有这个代码:

Payments = new ObservableCollection<PaymentViewModel>(_allPayments);

public ObservableCollection<PaymentViewModel> Payments
{
    get { return _payments; }
    set {
        _payments = value;
        RaisePropertyChanged("Payments");
    }
}

ObservableCollection我不明白和INotifyPropertyChanged这里有什么关系。你可以解释吗?

4

2 回答 2

9

ObservableCollection是一个专门的集合,可以在其内容更改时通知订阅者,而INotifyPropertyChanged它是一个接口,允许实现者在订阅者的某个属性更改值时通知订阅者。

您可能想知道这两者是如何相关的(因为在您的示例中,两者都“参与”了设置器)。

考虑这段代码:

var model = new MyViewModel(); // assume it's the class with Payments inside
model.Payments.Add(new PaymentViewModel());

事件的订阅者INotifyCollectionChanged.CollectionChanged现在会知道事情发生了变化,他们应该相应地更新。

但现在看看这个:

var model = new MyViewModel(); // assume it's the class with Payments inside
model.Payments.Add(new PaymentViewModel()); // OK, we know what this does

model.Payments = new ObservableCollection<PaymentViewModel>();

将一个项目添加到集合后,我们将整个集合换成另一个。如果 anItemsControl绑定到这个集合,我们希望它能够自我更新并反映model.Payments最终为空的事实。但它怎么能做到呢?

CollectionChanged将无济于事,因为原始集合(在收到第一个项目后)没有被修改;我们只是将其丢弃并在其位置安装了另一个。唯一知道切换发生的是Payments属性设置器。所以 setterINotifyPropertyChanged用来告诉订阅者该集合已被另一个替换,他们当然应该更新他们的状态。

结论:数据绑定在 WPF 中自动工作,因为所有数据绑定控件都侦听INotifyPropertyChanged它们的DataContext并且如果绑定目标实现INotifyCollectionChanged它们也会订阅它。如果绑定目标发生更改,则通过 通知他们INotifyPropertyChanged,从INotifyCollectionChanged旧目标上取消订阅并在新目标上订阅它。

于 2012-04-20T13:19:10.860 回答
2

一个 ObservableCollection 通知它的活页夹,例如当某些东西被添加/删除到集合本身时。

但是,您在第二个示例中所做的是通知活页夹该集合已被新集合替换(如果您执行新的 ObservableCollection,则 ObservableCollection 不会自行执行此操作-您会丢失绑定)。

于 2012-04-20T13:14:00.020 回答