Почему IList <>. Reverse () не работает как List <> (). Reverse - PullRequest
11 голосов
/ 12 января 2011

У меня проблемы с List<T>.Reverse() и Reverse(this IEnumerable<TSource> source).Посмотрите код:

  // Part 1
  List<int> list = new List<int> { 1, 2, 3 };

  foreach (int x in list)
    Console.Write(x);

  Console.WriteLine();

  list.Reverse();

  foreach (int x in list)
    Console.Write(x);

  Console.WriteLine();
  list.Reverse();

  // Part2
  IList<int> ilist = list;

  foreach (int x in list)
    Console.Write(x);      

  Console.WriteLine();

  ilist.Reverse();

  foreach (int x in ilist)
    Console.Write(x);

  Console.WriteLine();

  ilist.Reverse();

Мой результат:

123
321
123
123

, потому что Reverse() -Part1 это List<T>.Reverse(), Reverse() -Part2 это Reverse(this IEnumerable<TSource> source) Я хочу выполнить List<int>.Reverse() в части 2 для IList<int>.Как я могу это сделать?

Ответы [ 2 ]

9 голосов
/ 12 января 2011

IList<int> не имеет метода Reverse, поэтому он использует метод расширения.Единственный способ использовать List<T>.Reverse в вашем справочнике IList<int> - привести или преобразовать его в List<int>.Кастинг будет работать, только если вы уверены, что это действительно List<int> во-первых:

IList<int> abstractList;
var concreteList = (List<int>)abstractList;
concreteList.Reverse();

Другой вариант - создать a List<int> из вашего IList<int> экземпляр, вместо того, чтобы предполагать, что это уже List<int>:

IList<int> abstractList;
var concreteList = new List<int>(abstractList);
concreteList.Reverse();

причина , что метод расширения Reverse фактически не влияет на базовый список, потому что он работаетв IEnumerable<T>, который не обязательно доступен для записи (ни один из методов расширения Enumerable не вносит изменений в исходную коллекцию, они возвращают новую коллекцию).

Чтобы использовать эту версиюиз Reverse, просто используйте продукт вызова Reverse вместо исходного списка:

IList<int> abstractList;
IEnumerable<int> reversedList = abstractList.Reverse();
4 голосов
/ 12 января 2011

Во втором примере вы используете метод расширения для IEnumerable<T>, и это не изменяет исходную коллекцию, а создает запрос, который приводит к последовательности вашего исходного списка в обратном порядке. То есть, если вы хотите использовать результаты ilist.Reverse(), вы бы сказали

var reversedList = iList.Reverse(); 
// reversedList is IEnumerable<int>
// 'list' and 'ilist' are not changed

foreach (int item in reversedList)
    Console.Write(item);
...