ObservableCollection
是一种特殊的集合,当其 内容 发生变化时可以通知订阅者,而 INotifyPropertyChanged
是一个接口,允许实现者在其 属性 值改变时通知订阅者。
你可能想知道这两者之间的关系(因为在你的示例中,两者都“参与”了setter)。
考虑以下代码:
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>();
在向集合中添加项后,我们会将整个集合与另一个集合进行交换。如果一个ItemsControl
绑定到该集合,我们希望它能够更新自己,并反映出model.Payments
最终为空的事实。但它如何做到这一点呢?
CollectionChanged
无法帮助我们,因为原始集合(在收到第一项之后)没有被修改;我们只是丢弃了它并安装了另一个集合。唯一知道发生了切换的人是Payments
属性设置器。因此,这个设置器利用INotifyPropertyChanged
告诉订阅者集合已被替换为另一个集合,他们当然应该更新他们的状态。
结论:数据绑定在WPF中工作得自动化是因为所有的数据绑定控件都监听它们的DataContext
的INotifyPropertyChanged
,而如果绑定目标实现了INotifyCollectionChanged
,它们还会订阅它。如果绑定目标更改,它们通过INotifyPropertyChanged
得到通知,在旧目标上取消订阅INotifyCollectionChanged
,并在新目标上进行订阅。