Сортировка ObservableCollection C #

У меня ниже ObservableCollection . Мне нужно сортировать это в алфавитном порядке.

 private ObservableCollection _animals = new ObservableCollection { "Cat", "Dog", "Bear", "Lion", "Mouse", "Horse", "Rat", "Elephant", "Kangaroo", "Lizard", "Snake", "Frog", "Fish", "Butterfly", "Human", "Cow", "Bumble Bee" }; 

Я попробовал _animals.OrderByDescending . но я не знаю, как правильно его использовать.

 _animals.OrderByDescending(a => a.); 

Как я могу это сделать ?

Введение

В принципе, если необходимо отобразить отсортированную коллекцию, рассмотрите возможность использования classа CollectionViewSource : присвойте («привязать») его свойство Source к исходной коллекции – экземпляр classа ObservableCollection .

Идея состоит в том, что class CollectionViewSource предоставляет экземпляр classа CollectionView . Это своего рода «проекция» исходной (исходной) коллекции, но с применением сортировки, фильтрации и т. Д.

Рекомендации:

  • Практическое руководство. Сортировка и группировка данных с помощью представления в XAML .
  • Коллекция CollectionViewSource от WPF .

Live Shaping

WPF 4.5 представляет функцию «Live Shaping» для CollectionViewSource .

Рекомендации:

  • WPF 4.5 Новая функция: Live Shaping .
  • Свойство CollectionViewSource.IsLiveSorting .
  • Перемещение данных при изменении значений данных (форматирование в реальном времени) .

Решение

Если еще нужно отсортировать экземпляр classа ObservableCollection , вот как это можно сделать. Сам class ObservableCollection не имеет метода сортировки. Но коллекция могла быть воссоздана для сортировки предметов:

 // Animals property setter must raise "property changed" event to notify binding clients. // See INotifyPropertyChanged interface for details. Animals = new ObservableCollection { "Cat", "Dog", "Bear", "Lion", "Mouse", "Horse", "Rat", "Elephant", "Kangaroo", "Lizard", "Snake", "Frog", "Fish", "Butterfly", "Human", "Cow", "Bumble Bee" }; ... Animals = new ObservableCollection(Animals.OrderBy(i => i)); 

Дополнительные детали

Обратите внимание, что OrderBy() и OrderByDescending() (как другие методы расширения LINQ) не изменяют исходную коллекцию! Вместо этого они создают новую последовательность (то есть новый экземпляр classа, реализующий интерфейс IEnumerable ). Таким образом, необходимо воссоздать коллекцию.

Я знаю, это старый вопрос, но это первый результат google для «sort observablecollection», поэтому подумал, что стоит оставить мои два цента.

Путь

То, как я собирался, заключается в создании List<> начиная с ObservableCollection<> , сортировки его (с помощью метода Sort() , больше на msdn ), и когда List<> был отсортирован, измените порядок ObservableCollection<> на Move() .

Код

 public static void Sort(this ObservableCollection collection, Comparison comparison) { var sortableList = new List(collection); sortableList.Sort(comparison); for (int i = 0; i < sortableList.Count; i++) { collection.Move(collection.IndexOf(sortableList[i]), i); } } 

Тест

 public void TestObservableCollectionSortExtension() { var observableCollection = new ObservableCollection(); var maxValue = 10; // Populate the list in reverse mode [maxValue, maxValue-1, ..., 1, 0] for (int i = maxValue; i >= 0; i--) { observableCollection.Add(i); } // Assert the collection is in reverse mode for (int i = maxValue; i >= 0; i--) { Assert.AreEqual(i, observableCollection[maxValue - i]); } // Sort the observable collection observableCollection.Sort((a, b) => { return a.CompareTo(b); }); // Assert element have been sorted for (int i = 0; i < maxValue; i++) { Assert.AreEqual(i, observableCollection[i]); } } 

Я создал метод расширения для ObservableCollection

 public static void MySort(this ObservableCollection observableCollection, Func keySelector) { var a = observableCollection.OrderBy(keySelector).ToList(); observableCollection.Clear(); foreach(var b in a) { observableCollection.Add(b); } } 

Кажется, что это работает, и вам не нужно реализовывать IComparable

Я посмотрел на них, я его сортировал, а затем он сломал привязку, как указано выше. Придумал это решение, хотя и проще, чем большинство ваших, он, похоже, делает то, что я хочу,

 public static ObservableCollection OrderThoseGroups( ObservableCollection orderThoseGroups) { ObservableCollection temp; temp = new ObservableCollection(orderThoseGroups.OrderBy(p => p)); orderThoseGroups.Clear(); foreach (string j in temp) orderThoseGroups.Add(j); return orderThoseGroups; } 

Аргумент OrderByDescending – это функция, возвращающая ключ для сортировки. В вашем случае ключ является самой строкой:

 var result = _animals.OrderByDescending(a => a); 

Если вы хотите сортировать по длине, например, вы будете писать:

 var result = _animals.OrderByDescending(a => a.Length); 
 _animals.OrderByDescending(a => a.); 

Если животные будут списком объектов Animal, вы можете использовать свойство для заказа списка.

 public class Animal { public int ID {get; set;} public string Name {get; set;} ... } ObservableCollection animals = ... animals = animals.OrderByDescending(a => a.Name); 

Это ObservableCollection , который автоматически сортирует себя при изменении, запускает сортировку только тогда, когда это необходимо, и вызывает только одно действие изменения коллекции перемещения.

 using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Collections.Specialized; using System.Linq; namespace ConsoleApp4 { using static Console; public class SortableObservableCollection : ObservableCollection { public Func SortingSelector { get; set; } public bool Descending { get; set; } protected override void OnCollectionChanged(NotifyCollectionChangedEventArgs e) { base.OnCollectionChanged(e); if (e.Action != NotifyCollectionChangedAction.Reset && e.Action != NotifyCollectionChangedAction.Move && SortingSelector != null) { var query = this .Select((item, index) => (Item: item, Index: index)); query = Descending ? query.OrderBy(tuple => SortingSelector(tuple.Item)) : query.OrderByDescending(tuple => SortingSelector(tuple.Item)); var map = query.Select((tuple, index) => (OldIndex:tuple.Index, NewIndex:index)) .Where(o => o.OldIndex != o.NewIndex); using (var enumerator = map.GetEnumerator()) if (enumerator.MoveNext()) Move(enumerator.Current.OldIndex, enumerator.Current.NewIndex); } } } //USAGE class Program { static void Main(string[] args) { var xx = new SortableObservableCollection() { SortingSelector = i => i }; xx.CollectionChanged += (sender, e) => WriteLine($"action: {e.Action}, oldIndex:{e.OldStartingIndex}," + " newIndex:{e.NewStartingIndex}, newValue: {xx[e.NewStartingIndex]}"); xx.Add(10); xx.Add(8); xx.Add(45); xx.Add(0); xx.Add(100); xx.Add(-800); xx.Add(4857); xx.Add(-1); foreach (var item in xx) Write($"{item}, "); } } } 

Вывод:

 action: Add, oldIndex:-1, newIndex:0, newValue: 10 action: Add, oldIndex:-1, newIndex:1, newValue: 8 action: Move, oldIndex:1, newIndex:0, newValue: 8 action: Add, oldIndex:-1, newIndex:2, newValue: 45 action: Add, oldIndex:-1, newIndex:3, newValue: 0 action: Move, oldIndex:3, newIndex:0, newValue: 0 action: Add, oldIndex:-1, newIndex:4, newValue: 100 action: Add, oldIndex:-1, newIndex:5, newValue: -800 action: Move, oldIndex:5, newIndex:0, newValue: -800 action: Add, oldIndex:-1, newIndex:6, newValue: 4857 action: Add, oldIndex:-1, newIndex:7, newValue: -1 action: Move, oldIndex:7, newIndex:1, newValue: -1 -800, -1, 0, 8, 10, 45, 100, 4857, 
 myObservableCollection.ToList().Sort((x, y) => x.Property.CompareTo(y.Property)); 
 ///  /// Sorts the collection. ///  /// The type of the elements of the collection. /// The collection to sort. /// The comparison used for sorting. public static void Sort(this ObservableCollection collection, Comparison comparison = null) { var sortableList = new List(collection); if (comparison == null) sortableList.Sort(); else sortableList.Sort(comparison); for (var i = 0; i < sortableList.Count; i++) { var oldIndex = collection.IndexOf(sortableList[i]); var newIndex = i; if (oldIndex != newIndex) collection.Move(oldIndex, newIndex); } } 

Это решение основано на ответе Марко . У меня были некоторые проблемы с его решением, и поэтому он улучшил его, только вызвав Move если индекс действительно изменился. Это должно улучшить производительность, а также устранить связанную проблему.

  • Как объяснить сортировку (численное, лексикографическое и сопоставление) с примерами для нетехнических тестеров?
  • Правильно ли упорядочен порядок std :: pair ?
  • Сортировка по строке, которая может содержать число
  • Функция сортировки массива VBA?
  • Как отсортировать список словарей по значению словаря в Python?
  • ранг и порядок в R
  • Как сортировать быстрый массив, содержащий экземпляры подclassа NSManagedObject, по значению атрибута (date)
  • Сортировка словаря по ключам
  • Почему quicksort лучше, чем mergesort?
  • Как отсортировать массив объектов в Java?
  • Как сортировать аррайалист объектов по свойству?
  • Давайте будем гением компьютера.