This is a migrated thread and some comments may be shown as answers.

Cool ObservableCollection Sort Extension

1 Answer 291 Views
General Discussions
This is a migrated thread and some comments may be shown as answers.
Garry
Top achievements
Rank 1
Garry asked on 24 Jun 2010, 08:23 PM
I came across the need to be able to sort my ObservableCollections the other day and I found a nice code snippet demonstrating how to sort an ObservableCollection even if the collection type does not support IComparable. I added the ReverseCompare/Descending sort just in case. Anyhow thought it was a neat piece of code and hope it may help some others out there.

Enjoy!

public static class CollectionSorter  
    {  
        public static void Sort<T>(this ObservableCollection<T> collection, Comparison<T> comparison)  
        {  
            var comparer = new Comparer<T>(comparison);  
 
            List<T> sorted = collection.OrderBy(x => x, comparer).ToList();  
 
            for (int i = 0; i < sorted.Count(); i++)  
                collection.Move(collection.IndexOf(sorted[i]), i);  
        }  
 
        public static void DescendingSort<T>(this ObservableCollection<T> collection, Comparison<T> comparison)  
        {  
            var comparer = new ReverseComparer<T>(comparison);  
 
            List<T> sorted = collection.OrderBy(x => x, comparer).ToList();  
 
            for (int i = 0; i < sorted.Count(); i++)  
                collection.Move(collection.IndexOf(sorted[i]), i);  
        }       
    }  
 
    internal class Comparer<T> : IComparer<T>  
    {  
        private readonly Comparison<T> comparison;  
 
        public Comparer(Comparison<T> comparison)  
        {  
            this.comparison = comparison;  
        }
        #region IComparer<T> Members  
 
        public int Compare(T x, T y)  
        {  
            return comparison.Invoke(x, y);  
        }
        #endregion  
    }  
 
    internal class ReverseComparer<T> : IComparer<T>  
    {  
        private readonly Comparison<T> comparison;  
 
        public ReverseComparer(Comparison<T> comparison)  
        {  
            this.comparison = comparison;  
        }
        #region IComparer<T> Members  
 
        public int Compare(T x, T y)  
        {  
            return -comparison.Invoke(x, y);  
        }
        #endregion  
    } 

then you can use it on your ObservableCollections as such. 
private void Log(LogEntry log)  
        {  
            LoggedEvents.Add(log);  
            LoggedEvents.DescendingSort((x, y) => x.TimeStampString.CompareTo(y.TimeStampString));  
        }        
 
        private ObservableCollection<LogEntry> entries = new ObservableCollection<LogEntry>();  
        public ObservableCollection<LogEntry> LoggedEvents  
        {  
            get 
            {                  
                return entries;  
            }  
            set 
            {  
                entries = value;  
                RaisePropertyChanged(LoggedProperty);  
            }  
        } 

1 Answer, 1 is accepted

Sort by
0
Jonas
Top achievements
Rank 1
answered on 27 Nov 2012, 09:51 AM
The orderby-operation is fast, but since you do an indexof for each item in the list, the extension-method will have Ordo(n2) which is a bad thing... the collection should be ordered in place with a quicksort to keep performance good when working with large lists.
Tags
General Discussions
Asked by
Garry
Top achievements
Rank 1
Answers by
Jonas
Top achievements
Rank 1
Share this question
or