Sort an IList<T> in place

1.7k views Asked by At

If I have a List<T>, I can sort it in place using for example

myList.Sort((x,y) => x.MyComparisonMethod(y));

If I have an IList<T>, I can sort it into a new list using

var sortedIList = unsortedIList.OrderBy(x => x.SortingValue);

How can I sort an IList<T> in place?

I am using C# .NET 4.5.1.

3

There are 3 answers

1
Mathew Thompson On

I suspect you're referring to the fact that your OrderBy won't compile. That's because it returns an IOrderedEnumerable, which is not an IList, you'd have to perform ToList() afterwards to convert it back to an IList implementation:

var sortedIList = unsortedIList.OrderBy(x => x.SortingValue).ToList();

And if you want to use your own IComparer:

var sortedIList = unsortedIList.OrderBy(x => x.SortingValue, new MyComparer()).ToList();
11
Tim Schmelter On

" I can sort it into a new list using" no, that's not the case, OrderBy doesnt return a list, you have to call ToList to create a new list. Is your question how to use List.Sort with an IList<T> instead of a List<T>?

You can write an extension method for IList<T>:

public static IList<T> Sort<T>(this IEnumerable<T> sequence, IComparer<T> comparer = null)
{
    var seqList = sequence as List<T>;
    if (seqList != null)
    {
        seqList.Sort((IComparer<T>)comparer);
        return seqList;
    }

    var seqArray = sequence as T[];
    if (seqArray != null)
    {
        Array.Sort(seqArray, (IComparer<T>)comparer);
        return seqArray;
    }

    return sequence.OrderBy(t => t, (IComparer<T>)comparer).ToList();
}

Now you can use Sort on lists, arrays or any other kind of sequence:

IList<string> strings = new[] { "B", "A", "C" };
strings.Sort();

Update: if you just want one for arrays or lists you can use:

public static void Sort<T>(this IList<T> sequence, IComparer<T> comparer = null)
{
    var seqList = sequence as List<T>;
    if (seqList != null)
    {
        seqList.Sort((IComparer<T>)comparer);
        return;
    }

    var seqArray = sequence as T[];
    if (seqArray != null)
    {
        Array.Sort(seqArray, (IComparer<T>)comparer);
    }
}
2
Francesco De Lisi On

Write your own extension method using ArrayList.Adapter as IList<T> wrapper and your own CustomComparer starting from some Comparison delegate:

public static class IListExtensions
{
    public static void Sort<T>(this IList<T> list, Comparison<T> comparison)
    {
        ArrayList.Adapter((IList)list).Sort(new CustomComparer<T>(comparison));
    }
}