Что ж, наличие статического компаратора означает, что вы не можете иметь разные сравнения в разных очередях; это может быть проблемой ... иногда люди делают нуждаются в пользовательском сравнении; например, если они не контролируют тип. Мой подход по умолчанию будет:
PriorityQueue<TPriority>
{
private IComparer<TPriority> _comparer;
public PriorityQueue(IComparer<TPriority> comparer) {
_comparer = comparer;
...
}
public PriorityQueue() : this(Comparer<T>.Default) {}
}
Re Stateful сравнения; да, я написал несколько - особенно для написания проекционных компараторов в стиле LINQ ... например, что-то вроде:
public static class ProjectionComparer<TSource>
{
public static IComparer<TSource> CompareBy<TValue>(
Func<TSource, TValue> selector)
{
return CompareBy<TValue>(selector, Comparer<TValue>.Default);
}
public static IComparer<TSource> CompareBy<TValue>(
Func<TSource, TValue> selector,
IComparer<TValue> comparer)
{
return new ProjectionComparerItem<TValue>(
selector, Comparer<TValue>.Default);
}
class ProjectionComparerItem<TValue> : IComparer<TSource>
{
private readonly IComparer<TValue> comparer;
private readonly Func<TSource, TValue> selector;
public ProjectionComparerItem(
Func<TSource, TValue> selector,
IComparer<TValue> comparer)
{
this.selector = selector;
this.comparer = comparer;
}
public int Compare(TSource x, TSource y)
{
// TODO: some null stuff...
return comparer.Compare(selector(x), selector(y));
}
}
}
, что позволяет:
IComparer<Customer> comparer = ProjectionComparer<Customer>
.CompareBy(cust => cust.Name);
Экземпляр "сортировка по имени" сравнения.