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の1つが値を変更したときに、実装者がサブスクライバーに通知できるインターフェイスです。

あなたはおそらく、2つがどのように関連しているのか疑問に思っているでしょう(あなたの例では両方がセッターに「関与している」ため)。

このコードを考えてみましょう:

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で自動的に機能します。これは、すべてのデータバインディングコントロールがのをリッスンしバインディングターゲットが実装されている場合は、INotifyPropertyChangedそれらもサブスクライブするためです。バインディングターゲットが変更された場合は、を通じて通知され、古いターゲットでサブスクライブを解除し、新しいターゲットでサブスクライブします。DataContextINotifyCollectionChangedINotifyPropertyChangedINotifyCollectionChanged

于 2012-04-20T13:19:10.860 に答える
2

ObservableCollectionは、たとえばコレクション自体に何かが追加/削除されたときに、そのバインダーに通知します。

ただし、2番目の例で行っているのは、コレクションが新しいコレクションに置き換えられたことをバインダーに通知することです(新しいObservableCollectionを実行すると、ObservableCollectionはそれ自体を実行しません-そこでバインディングが失われます)。

于 2012-04-20T13:14:00.020 に答える