Reputation: 213
Is possible to order on Linq according to a specific order? something like
List<bbHeader> bb = new List<bbHeader>();
bb.OrderBy(x => x.Country.CompareTo(new string[]{"AR","CL","PY","UY","AUP"}));
The idea is that the Country field is ordered according to the specific order of the string
Upvotes: 9
Views: 2885
Reputation: 38397
There's a very direct way in your example:
var sequence = new [] { "AR", "CL", "PY", "UY", "AUP" };
List<bbHeader> bb = new List<bbHeadher>();
// fill bb
// takes the item, checks the index of the country in the array
var result = bb.OrderBy(x => Array.IndexOf(sequence, x.Country));
In this way, you are ordering by the index Country is found in the sequence string. Just keep in mind that not-found items will be -1, which you can correct for also if you like.
If you want to do anything more complex, you can to create your own custom IComparer
class implementation to compare the items using your custom order. This can then be passed into OrderBy.
Such an IComparer would look like:
public sealed class SequenceComparer : IComparer<string>
{
private string[] _sequence { get; set; }
public SequenceComparer(string[] sequence)
{
if (sequence == null) throw new ArgumentNullException("sequence");
_sequence = sequence;
}
public int Compare(string x, string y)
{
if (ReferenceEquals(x, y)) return 0;
return Array.IndexOf(_sequence, x).CompareTo(Array.IndexOf(_sequence, y));
}
}
And can be called like:
var result = bb.OrderBy(x => x.Country, new SequenceComparer(new [] { "AR", "CL", "PY", "UY", "AUP" }));
Either way works well, the latter is nice and reusable, but the former (using IndexOf directly) is still very concise as well. Your choice.
Upvotes: 17
Reputation: 15579
well you can pass in your own delegate to orderby function and the comparison logic in that case can be defined by you.
Upvotes: 1