2017-02-15 4 views
2

У меня есть словарь <string, Point> и ключи в этом словаре выглядеть следующим образом:C# макс() не возвращает естественное самое высокое значение

  • char_1_1
  • char_1_2
  • ...
  • char_1_9
  • char_1_10

Теперь я использую следующий сек tatement получить heighest значения ключей:

pointsWhichBelongTogether.Keys.Where(key => key.Contains(searchStringPattern[0] + "_" + searchStringPattern[1] + "_")).OrderBy(x => x, new NaturalStringComparer()).Max() 

который использует следующий Compare-Class:

public class NaturalStringComparer : IComparer<string> 
    { 
     private static readonly Regex _re = new Regex(@"(?<=\D)(?=\d)|(?<=\d)(?=\D)", RegexOptions.Compiled); 

     public int Compare(string x, string y) 
     { 
      x = x.ToLower(); 
      y = y.ToLower(); 
      if (string.Compare(x, 0, y, 0, Math.Min(x.Length, y.Length)) == 0) 
      { 
       if (x.Length == y.Length) return 0; 
       return x.Length < y.Length ? -1 : 1; 
      } 
      var a = _re.Split(x); 
      var b = _re.Split(y); 
      int i = 0; 
      while (true) 
      { 
       int r = PartCompare(a[i], b[i]); 
       if (r != 0) return r; 
       ++i; 
      } 
     } 

     private static int PartCompare(string x, string y) 
     { 
      int a, b; 
      if (int.TryParse(x, out a) && int.TryParse(y, out b)) 
       return a.CompareTo(b); 
      return x.CompareTo(y); 
     } 
    } 

Так я полагаю, что этот список естественно сортируется и Max-функция просто получает самое высокую стоимость. Но max() возвращает char_1_9 как самое высокое значение. Эта функция max() - повторная сортировка?

+1

, так как вы sotring строки (а не числа), 'char_1_9' на самом деле считается больше, чем' char_1_10'. –

+0

Заказ коллекции перед вызовом 'Max()' делает что именно? Вы просто вызываете 'IEnumerable .Max()'. – CodeCaster

+0

Но я сделал естественный Сортировка раньше? – Snickbrack

ответ

5

У вас есть два варианта:

  • Возьмите Last из отсортированного списка или
  • убывающем порядке и сделать первый

Прямо сейчас вы сортировки, используя свой компаратор, но Max не используйте компаратор, но сравнитель по умолчанию, чтобы найти максимальное значение.

pointsWhichBelongTogether.Keys.Where(key => key.Contains(searchStringPattern[0] + "_" + searchStringPattern[1] + "_")) 
    .OrderBy(x => x, new NaturalStringComparer()).Last(); 

или

pointsWhichBelongTogether.Keys.Where(key => key.Contains(searchStringPattern[0] + "_" + searchStringPattern[1] + "_")) 
    .OrderByDescending(x => x, new NaturalStringComparer()).First(); 

Edit: в предыдущей версии я предложил передать компаратор в Max, но, кажется, нет никакой перегрузки, которая принимает компаратор, только селектор.

+0

Это хорошо. Вот что я буду использовать! Благодаря! – Snickbrack

+0

@Snickbrack это была ошибка копирования и вставки, я все еще искал перегрузку Max, которая берет компаратор и забыла удалить эту незавершенную строку. –

1

Тип string уже реализует IComparable<string>, поэтому Max() использует эту реализацию независимо от предыдущей сортировки. Я хотел бы заказать значения нисходящие и взять первое значение:

var max = pointsWhichBelongTogether.Keys 
    .Where(key => key.Contains(searchStringPattern[0] + "_" + searchStringPattern[1] + "_")) 
    .OrderByDescending(x => x, new NaturalStringComparer()) 
    .FirstOrDefault(); 
Смежные вопросы