C # /. NET / WPF: получение подмножеств из LINQ, а не IEnumerable - PullRequest
1 голос
/ 02 сентября 2010

У меня есть некоторый тривиальный код, который выглядит следующим образом:

SortedDictionary<String, long> d = new SortedDictionary<String, long>();
// d is then populated with an expensive time-consuming process

ListBox lb = new ListBox();
lb.ItemsSource = d;                                      // THIS WORKS GREAT

Теперь я хотел бы динамически отображать подмножество словаря без его перерасчета.

// min is assigned somewhere else
lb.ItemsSource = d.SkipWhile( kvp => kvp.Value < min );  // THIS DOESN'T WORK

.SkipWhile () возвращает IEnumerable, который отлично подходит для циклов foreach, но не так актуален для ItemsSource.

A) Есть ли способ передать LINQ-подобное выражение в элемент управления WPF таким образом?

B) Если это не так, есть ли способ сделать что-то вроде:

// Put things back, like the .ToArray() syntax
d.SkipWhile( kvp => kvp.Value < min).ToSortedDictionary();

C) Если это не так, есть ли способ условно удалить записи из фактического словаря?

d.RemoveWhere( kvp => kvp.Value < min );


UPDATE : Фильтрация не работает от того, что я ожидал. Оказывается, мое понимание .SkipWhile () было неверным, основываясь на исходном источнике документации.

// This is what I was seeing and seemed strange
Console.WriteLine("Total = " + dict.Count");
Console.WriteLine(" Skip = " + dict.SkipWhile( kvp => kvp.Value < 3 ).Count());
foreach ( var kvp in dict.SkipWhile( kvp => kvp.Value < 3 ) ) {
  Console.WriteLine( kvp );
}

Результат:

Total = 33350
 Skip = 33350
[ 0, 1042 ]
[ 00, 52 ]
[ 000, 55 ] 
[ 001, 1 ]
[ 002, 1 ]
[ 003, 1 ]
...

Я не ожидал, что строки с .Value меньше трех.

Использование .Where () вместо этого, как объяснено в ответе, решило проблему.

1 Ответ

3 голосов
/ 02 сентября 2010

SortedDictionary сортируется по ключу, а не по значению, поэтому метод SkipWhile не будет пропускать все элементы, где значение меньше минимального, он будет начинаться с наименьшего ключа и пропускает только элементы до находит элемент, значение которого больше или равно минимальному.

Если вы хотите отфильтровать все элементы, значение которых меньше минимального, используйте метод Where:

lb.ItemsSource = s.Where(kvp => kvp.Value < min);

Это создает выражение, которое читает из SortedDictionary по мере необходимости.

...