ObservableCollectionとBindingListの違い


236

私は間の違いを知ってほしいObservableCollectionBindingList私はソースのいずれかの追加/削除の変更を通知するために両方を使用しましたので、他の上で1つを好むとき、私は実際にはわかりません。

次のいずれかを選択するのはなぜですか?

ObservableCollection<Employee> lstEmp = new ObservableCollection<Employee>();

または

BindingList<Employee> lstEmp = new BindingList<Employee>();

回答:


278

ObservableCollectionまさにすべてのコレクションのようなUIから更新することができます。真の違いはかなり単純です。

ObservableCollection<T>INotifyCollectionChangedコレクションが変更されたときに通知を提供する実装(あなたは^^を推測しました)を更新すると、バインディングエンジンはUIを更新できますObservableCollection

ただし、をBindingList<T>実装しIBindingListます。

IBindingListコレクションの変更に関する通知を提供しますが、それだけではありません。次のような変更に応じてUIを更新するだけではなく、UIで使用できる機能をすべて提供します。

  • 仕分け
  • 探す
  • ファクトリーを通じて追加します(AddNewメンバー関数)。
  • 読み取り専用リスト(CanEditプロパティ)

これらの機能はすべて、 ObservableCollection<T>

もう1つの違いはBindingList、アイテムの実装時にアイテム変更通知を中継することINotifyPropertyChangedです。項目が提起した場合PropertyChanged、イベントを、BindingList発生させ、それを受信するListChangedEventListChangedType.ItemChangedOldIndex=NewIndex(アイテムが交換された場合、OldIndex=-1)。ObservableCollectionアイテム通知を中継しません。

Silverlightでは、BindingListはオプションとして使用できないことに注意してください。ただし、ObservableCollectionsとICollectionViewIPagedCollectionView私がよく覚えている場合)を使用できます。


5
考慮すべきもう1つのことはパフォーマンスです。次を参照してください。themissingdocs.net
Jarek Mazur

ありがとう、BindingListの実際の実装については知りませんでした。私はObservableCollectionおよびICollectionViewを使用する傾向があります
Eilistraee

5
この回答の情報は正しいですが、WPFユーザーは注意する必要があります。BindingListはINotifyCollectionChangedを実装していないため、コントロールのItemsSourceプロパティにバインドするとメモリリークが発生します。ObservableCollectionはインターフェイスを実装しているため、このようなリークは発生しません。
Brandon Hood

1
BindingListがソートを実装する場合、BindingListにバインドされたグリッドをソートできないのはなぜですか?
Robert Harvey

あるBindingList時代遅れ?
Shimmy Weitzhandler

27

実際の違いは、BindingListがWinForms用であり、ObservableCollectionがWPF用であることです。

WPFの観点から見ると、BindingListは適切にサポートされておらず、本当に必要な場合を除いて、WPFプロジェクトで実際に使用することは決してありません。


1
面白い。Silverlight開発者として、私はそれを知りませんでした。ありがとう。そして、並べ替えとフィルタリングが必要な場合は、ICollectionViewの実装がお
役に立ち

27
なぜ「サポートされていない」のですか?ViewManager(内部)はPresentationFrameworkアセンブリ内にあり、それをサポートしています。たとえば、ItemsControlにバインドすると、変更通知が尊重されます(つまり、アイテムが追加および削除されます)。WinForms固有の場合は、Forms名前空間に配置した方がよいでしょうか。
David Kiff、

7
Davidと同意し、それはSystem.Collections名前空間にあるため、WPFで完全にサポートされるはずです。WPFは、UIレイアウトの別の方法です。
ジャスティン

13
Davidにも同意します。ObservableCollectionは項目からのプロパティ変更通知をバブルアップしないため、WPFでBindingListを頻繁に使用します。
amnesia

3
"not supportet"の例を示します。WPFアプリケーションで、INotifyCollectionChangedを実装していない一部のBindingListsによって引き起こされるメモリリークを発見しました
Breeze

4

含まれている要素に関する機能や変更通知などの最も重要な違いは、受け入れられた回答で既に言及されていますが、他にも言及する価値があるものがあります。

パフォーマンス

ときはAddNew、呼び出されたBindingList<T>ことにより、追加したアイテムを検索IndexOf検索。変更された要素のインデックスをT実装してINotifyPropertyChangedいる場合も検索されますIndexOf(ただし、同じアイテムが繰り返し変更される限り、新しいルックアップはありません)。コレクションに何千もの要素を格納する場合、ObservableCollection<T>(またはIBindingListO(1)ルックアップコストを使用したカスタム実装)の方が望ましい場合があります。

完全

  • IBindingListインタフェースは、巨大な1(そうでないかもしれないクリーンなデザイン)で、実装者は、その機能のサブセットのみを実装することができます。例えばAllowNewSupportsSorting及びSupportsSearching特性がかどうかを伝えAddNewApplySort及びFind方法は、それぞれ、使用することができます。それBindingList<T>自体が並べ替えをサポートしていないことは、しばしば人々を驚かせます。実際には、派生クラスに不足している機能を追加させる仮想メソッドがいくつか提供されています。DataViewクラスは、完全のための例示であり、IBindingList実装。ただし、そもそも型付きコレクション用ではありません。また、BindingSourceWinForms のクラスはハイブリッドの例ですIBindingList。並べ替えをサポートする別の実装をラップする場合は、並べ替えをサポートします。

  • ObservableCollection<T>INotifyCollectionChangedインターフェースの完全な実装です(単一のイベントのみ)。また、仮想メンバーもありますが、ObservableCollection<T>通常はその基本Collection<T>クラスと同じ理由で派生します。バインディング機能を調整するのではなく、アイテムの追加/削除(たとえば、データモデルコレクション内)をカスタマイズするためです。

コピーとラッピング

両方ObservableCollection<T>BindingList<T>既存のリストを受け取るコンストラクタを持っています。ただし、別のコレクションによってインスタンス化された場合、動作は異なります。

  • BindingList<T>提供されたリストの監視可能なラッパーとして機能し、変更はBindingList<T>は、基になるコレクションにも反映されます。
  • ObservableCollection<T>一方、新しいList<T>インスタンスを基本Collection<T>コンストラクターに渡し、元のコレクションの要素をこの新しいリストにコピーします。もちろん、T参照タイプの場合、要素の変更は元のコレクションから表示されますが、コレクション自体は更新されません。

1

ワン・モア大きな違いの間ObservableCollectionBindingList便利な付属しており、トピックに関する入札の決定要因となることができます。

BindingList リスト変更ハンドラー:

BindingListリストの変更

ObservableCollection コレクションの変更:

ObervableCollectionコレクションが変更されました

上記の概要:でアイテムのプロパティが変更されたBindingList場合、ListChangedイベントは(PropertyDescriptor内の)プロパティの完全な詳細をObservableCollection提供し、それを提供しません。実際 ObservableCollection、アイテムで変更されたプロパティの変更イベントは発生しません。

上記の結論は、INotifyPropertyChangedモデルクラスでの実装に関するものです。デフォルトでは、項目でプロパティが変更された場合、noneはchangedイベントを発生させません。


これ(PropertyDescriptor)がメモリリークの原因である可能性があると思います
Abdulkarim Kanaan 2018
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.