Bagaimana saya bisa mengurutkan IEnumerable<string>
menurut abjad. Apakah ini mungkin?
Sunting: Bagaimana saya menulis solusi di tempat?
Jawaban:
Dengan cara yang sama Anda mengurutkan yang lain yang dapat dihitung:
var result = myEnumerable.OrderBy(s => s);
atau
var result = from s in myEnumerable
orderby s
select s;
atau (mengabaikan kasus)
var result = myEnumerable.OrderBy(s => s,
StringComparer.CurrentCultureIgnoreCase);
Perhatikan bahwa, seperti biasa dengan LINQ, ini membuat IEnumerable <T> baru yang, ketika disebutkan, mengembalikan elemen IEnumerable <T> asli dalam urutan yang diurutkan. Itu tidak mengurutkan IEnumerable <T> di tempat.
IEnumerable <T> bersifat read-only, artinya, Anda hanya dapat mengambil elemen darinya, tetapi tidak dapat memodifikasinya secara langsung. Jika Anda ingin mengurutkan kumpulan string di tempat, Anda perlu mengurutkan koleksi asli yang mengimplementasikan IEnumerable <string>, atau mengubah IEnumerable <string> menjadi koleksi yang dapat diurutkan terlebih dahulu:
List<string> myList = myEnumerable.ToList();
myList.Sort();
Berdasarkan komentar Anda:
_components = (from c in xml.Descendants("component")
let value = (string)c
orderby value
select value
)
.Distinct()
.ToList();
atau
_components = xml.Descendants("component")
.Select(c => (string)c)
.Distinct()
.OrderBy(v => v)
.ToList();
atau (jika nanti Anda ingin menambahkan lebih banyak item ke daftar dan tetap mengurutkannya)
_components = xml.Descendants("component")
.Select(c => (string)c)
.Distinct()
.ToList();
_components.Add("foo");
_components.Sort();
OrderBy
kembali IOrderedEnumerable<T>
. IOrderedEnumerable<T>
berasal dari IEnumerable<T>
sehingga dapat digunakan seperti IEnumerable<T>
, tetapi memperluas jenis, memungkinkan misalnya, untuk penggunaan ThenBy
.
Itu tidak mungkin, tetapi sebenarnya tidak.
Pada dasarnya, metode pengurutan apa pun akan menyalin Anda IEnumerable
ke dalam List
, mengurutkan, List
dan kemudian mengembalikan kepada Anda daftar yang diurutkan, yang IEnumerable
juga merupakan IList
.
Ini berarti Anda kehilangan properti "lanjutkan tanpa batas" dari sebuah IEnumerable
, tetapi Anda tidak dapat mengurutkan yang seperti itu.
Kami tidak selalu dapat melakukannya di tempat, tetapi kami mendeteksi jika memungkinkan:
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);
}
Ini menggunakan struct praktis berikut:
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);
}
}
listToSort = (src is List<T>) ? (List<T>)src : new List<T>(src);
? Bagaimana kalau memilikinyalistToSort = (src as List<T>); if (null == listToSort) listToSort = new List<T>(src);