Wie kann ich einen IEnumerable<string>
Alphabetisch sortieren? Ist das möglich?
Edit: Wie würde ich eine In-Place-Lösung schreiben?
So wie Sie jede andere Aufzählung sortieren würden:
var result = myEnumerable.OrderBy(s => s);
oder
var result = from s in myEnumerable
orderby s
select s;
oder (Groß-/Kleinschreibung ignorieren)
var result = myEnumerable.OrderBy(s => s,
StringComparer.CurrentCultureIgnoreCase);
Beachten Sie, dass wie bei LINQ üblich ein neues IEnumerable <T> erstellt wird, das bei Aufzählung die Elemente des ursprünglichen IEnumerable <T> in sortierter Reihenfolge zurückgibt. IEnumerable <T> wird nicht direkt sortiert.
Ein IEnumerable <T> ist schreibgeschützt, dh, Sie können nur die Elemente daraus abrufen, aber nicht direkt ändern. Wenn Sie eine Sammlung von Zeichenfolgen direkt sortieren möchten, müssen Sie die ursprüngliche Sammlung sortieren, in der IEnumerable <string> implementiert ist, oder zuerst IEnumerable <string> in eine sortierbare Sammlung umwandeln:
List<string> myList = myEnumerable.ToList();
myList.Sort();
Basierend auf Ihrem Kommentar:
_components = (from c in xml.Descendants("component")
let value = (string)c
orderby value
select value
)
.Distinct()
.ToList();
oder
_components = xml.Descendants("component")
.Select(c => (string)c)
.Distinct()
.OrderBy(v => v)
.ToList();
oder (wenn Sie der Liste später weitere Elemente hinzufügen und sie sortiert lassen möchten)
_components = xml.Descendants("component")
.Select(c => (string)c)
.Distinct()
.ToList();
_components.Add("foo");
_components.Sort();
Es ist unmöglich, aber es ist nicht möglich.
Grundsätzlich wird jede Sortiermethode Ihre IEnumerable
in eine List
kopieren, die List
sortieren und dann die sortierte Liste, die eine IEnumerable
ist, an Sie zurückgeben. ] sowie ein IList
.
Dies bedeutet, dass Sie die Eigenschaft "unendlich weitermachen" eines IEnumerable
verlieren, aber dann können Sie sowieso keine solche sortieren.
myEnumerable = myEnumerable.OrderBy(s => s);
Wir können dies nicht immer vor Ort tun, aber wir erkennen, wann es möglich ist:
IEnumerable<T> SortInPlaceIfCan(IEnumerable<T> src, IComparer<T> cmp)
{
List<T> listToSort = (src is List<T>) ? (List<T>)src : new List<T>(src);
listToSort.Sort(cmp);
return listToSort;
}
IEnumerable<T> SortInPlaceIfCan(IEnumerable<T> src, Comparison<T> cmp)
{
return SortInPlaceIfCan(src, new FuncComparer<T>(cmp));
}
IEnumerable<T> SortInPlaceIfCan(IEnumerable<T> src)
{
return SortInPlaceIfCan(src, Comparer<T>.Default);
}
Dies verwendet die folgende handliche Struktur:
internal struct FuncComparer<T> : IComparer<T>
{
private readonly Comparison<T> _cmp;
public FuncComparer(Comparison<T> cmp)
{
_cmp = cmp;
}
public int Compare(T x, T y)
{
return _cmp(x, y);
}
}