ObservableCollection投影也是可观察的

时间:2014-02-28 07:49:48

标签: c# linq windows-phone-8 collections observablecollection

我在mz ViewModel中有一个可观察的项目集合,比如说

public ObservableCollection<T> Items {get;private set;}

我在View中使用没有问题。我想创建一个这个集合的投影,这也是可观察的。像

这样的东西
public IEnumerable<T> ProjectedItems
{
   get 
   {
        Items.OrderByDescending(l=>l.SomeProperty).Take(SomeAmount);
   }
}

这个想法是当Items更改时,ProjectedItems也会改变(重新评估LINQ表达式)。有没有办法实现这个目标?

3 个答案:

答案 0 :(得分:1)

有关

public ObservableCollection<T> Items {get;private set;}
public IEnumerable<T> ProjectedItems  {get;private set;}

似乎有效的解决方案是订阅CollectionChanged ObservableCollection事件并重新评估LINQ表达式:

Items.CollectionChanged += (s, e) => ProjectedItems = Items.OrderByDescending(l=>l.SomeProperty).Take(SomeAmount);

答案 1 :(得分:1)

首先,如果您正在执行绑定,请不要使用IEnumerable<T>,因为延迟执行可能会产生一些有趣的副作用。请改用IListICollection

也就是说,您应该根据原始集合的变化频率和变更时间来设计策略,以确定有多少项目会发生变化。如果更改的数量很多,那么自己实际处理元素的提取可能会更高效,否则只要原始集合发生更改,您就可以简单地重新构建列表。

答案 2 :(得分:0)

CollectionViewSource来对ObservableCollection的项进行分组,过滤和排序(如果你启用&#34; live&#34;分组/过滤/排序,则动态),但据我所知无法在ObservableCollections上使用所有LINQ运算符。

您可以实现自己的INotifyCollectionChanged包围现有的ObservableCollection,对其应用一些方法(例如TakeOrderBy),并触发CollectionChanged每当包装的集合发生时。