要素が次のリストがあります:
struct element {
double priority;
int value;
}
リストを優先度で並べ替えることができる独自の比較機能を実装するにはどうすればよいですか?SortredListを試してみましたが、重複したキーは許可されていません:(
助けてくれてありがとう!
要素が次のリストがあります:
struct element {
double priority;
int value;
}
リストを優先度で並べ替えることができる独自の比較機能を実装するにはどうすればよいですか?SortredListを試してみましたが、重複したキーは許可されていません:(
助けてくれてありがとう!
C#3以降を想定:
var sorted = MyList.OrderBy(e => e.priority);
デリゲートを使用するSort
オーバーロードを使用して、インプレースソートを実行できます。Comparison<T>
yourList.Sort((x, y) => x.priority.CompareTo(y.priority));
古いバージョンのC#の場合、ラムダを旧式のデリゲート構文に交換する必要があります。
yourList.Sort(
delegate(element x, element y) { return x.priority.CompareTo(y.priority); });
C#3拡張機能またはLambdasに依存できない場合は、次のように、構造体にIComparableインターフェイスを実装させることができます。
struct element : IComparable
{
double priority;
int value;
public element(int val, double prio)
{
priority = prio;
value = val;
}
#region IComparable Members
public int CompareTo(object obj)
{
// throws exception if type is wrong
element other = (element)obj;
return priority.CompareTo(other.priority);
}
#endregion
}
このインターフェースのタイプセーフバージョンもありますが、原則は同じです
構造体またはクラスにそのインターフェイスを実装した後、Sortメソッドを呼び出すList<>
と「正常に機能」します
static void Main(string[] args)
{
Random r = new Random();
List<element> myList = new List<element>();
for (int i = 0; i < 10; i++)
myList.Add(new element(r.Next(), r.NextDouble()));
// List is now unsorted
myList.Sort();
// List is now sorted by priority
Console.ReadLine();
}
これは、リスト自体を並べ替えるのか、(リストを変更せずに)並べ替えられた順序で値を取得するのかによって異なります。
List<element>
リスト自体をソートするには(と呼ばれるものがあると仮定しますelements
):
elements.Sort((x, y) => x.priority.CompareTo(y.priority));
// now elements is sorted
.NET 2.0と同等:
elements.Sort(
delegate(element x, element y) {
return x.priority.CompareTo(y.priority);
}
);
ソートされた順序で値を取得するには:
var orderedElements = elements.OrderBy(x => x.priority);
// elements remains the same, but orderedElements will retrieve them in order
.NET 2.0には同等のLINQはありませんが、独自に作成できます。
public static IEnumerable<T> OrderBy<T>(IEnumerable<T> source, Comparison<T> comparison) {
List<T> copy = new List<T>(source);
copy.Sort(comparison);
foreach (T item in copy)
yield return item;
}
使用法:
Comparison<element> compareByPriority = delegate(element x, element y) {
return x.priority.CompareTo(y.priority);
};
// unfortunately .NET 2.0 doesn't support extension methods, so this has to be
// expressed as a regular static method
IEnumerable<element> orderedElements = OrderBy(elements, compareByPriority);
新しいインスタンスを作成せずにリスト自体を並べ替える場合は、IComparerを実装してから、実装のインスタンスを使用してList.Sortを呼び出すことができます。
public class ElementComparer : IComparer<element>
{
public int Compare(element x, element y)
{
throw new NotImplementedException();
}
}