20

我有一个可观察的集合,我使用 linq 对其进行排序。一切都很好,但我遇到的问题是如何对实际的 observable 集合进行排序?相反,我只是得到了一些 IEnumerable 的东西,我最终清除了集合并重新添加了东西。这对性能没有好处。有谁知道更好的方法来做到这一点?

4

6 回答 6

15

如果您使用的是 Silverlight 3.0,那么使用 CollectionViewSource 是最简洁的方法。请参考以下示例:(也可以通过 xaml 完成)

ObservableCollection<DateTime> ecAll = new ObservableCollection<DateTime>();
CollectionViewSource sortedcvs = new CollectionViewSource();
sortedcvs.SortDescriptions.Add(new System.ComponentModel.SortDescription("Date", 
    System.ComponentModel.ListSortDirection.Ascending));
sortedcvs.Source = ecAll;
ListBoxContainer.DataContext = sortedcvs;

并在相应的 xaml 集中

ItemsSource="{Binding}"

对于 ListBox 或任何 ItemsControl 派生控件

于 2009-08-05T13:12:55.520 回答
9

由于该集合不提供任何Sort机制,因此这可能是最实用的选择。您可以使用 etc 手动实现排序Move,但它可能会比以这种方式执行的要慢。

    var arr = list.OrderBy(x => x.SomeProp).ToArray();
    list.Clear();
    foreach (var item in arr) {
        list.Add(item);
    }

此外,您可能会考虑在排序时取消绑定任何 UI 元素(通过任一方法),您只需支付重新绑定一次费用:

有趣的是,如果这是BindingList<T>,您可以使用RaiseListChangedEvents来最小化通知的数量:

    var arr = list.OrderBy(x => x).ToArray();
    bool oldRaise = list.RaiseListChangedEvents;
    list.RaiseListChangedEvents = false;
    try {
        list.Clear();
        foreach (var item in arr) {
            list.Add(item);
        }
    } finally {
        list.RaiseListChangedEvents = oldRaise;
        if (oldRaise) list.ResetBindings();
    }
于 2009-06-15T13:35:46.047 回答
3

请注意,在 Linq 中,您会从查询中获得一个 IEnumerable,并且该查询尚未执行。因此,以下代码只运行一次查询,将其添加到 ObservableCollection:

var query = from x in Data
            where x.Tag == "Something"
            select x;

foreach(var item in query)
    MyObservableCollection.Add(item);

看看 IEnumerable 上的“ OrderBy ”扩展:

foreach(var item in query.OrderBy(x => x.Name))
    MyObservableCollection.Add(item);
于 2009-06-15T13:33:36.597 回答
3

ObservableCollections 并非设计为可排序的。List 是可排序的,这是引用 List.Sort() 的答案所使用的底层机制,但 ObservableCollection 不是从 List 派生的,所以你在那里不走运。Imo,“正确”的解决方案不是尝试对 ObservableCollection 进行排序,而是实现 ICollectionView 并将其实例绑定到您的控件。该接口添加了用于排序的方法,并具有 Silverlight 控件(好吧,无论如何都支持它的控件,例如 DataGrid)识别的额外好处,因此您的排序可以直接从 UI 层使用。这个问题可能会有所帮助:

Silverlight 和 icollectionview

于 2009-06-15T14:06:20.933 回答
0

我按照这篇文章中提到的链接http://mokosh.co.uk/post/2009/08/04/how-to-sort-observablecollection/comment-page-1/#comment-75

但在 Silverlight 中运行时遇到问题

我创建了一个属性 public SortableObservableCollection 条款 当我调用 Terms.Sort(new TermComparer()) 时,记录仍然在 UI 上显示未排序

有人可以建议可能出了什么问题。谢谢

于 2010-05-27T00:25:44.783 回答
0

我在 CodePlex 上找到了这个:

排序集合

不过还没用过。

瑞克

于 2010-06-04T21:22:55.667 回答