У меня есть список:
List<int> list = new List<int> { 1, 2, 3, 4, 5 };
Я хочу применить некоторую трансформацию к элементам моего списка. Я могу сделать это двумя способами:
List<int> list1 = list.Select(x => 2 * x).ToList();
List<int> list2 = list.ConvertAll(x => 2 * x).ToList();
В чем разница между этими двумя способами?
Ответы:
Select
является методом расширения LINQ и работает со всемиIEnumerable<T>
объектами, тогдаConvertAll
как реализуется только с помощьюList<T>
. ЭтотConvertAll
метод существует с .NET 2.0, тогда как LINQ был представлен в версии 3.5.Вы должны способствовать
Select
более ,ConvertAll
как это работает для любого вида списка, но они делают то же самое в принципе.источник
Select
иConvertAll
. Первый выбирает каждый элемент в последовательности, и вы можете делать с ним все, что хотите. У последнего есть четкое намерение: преобразовать этот предмет во что-нибудь другое.ConvertAll
не является расширением, это метод класса списка. Вам не нужно вызыватьToList
результат, так как это уже список:Итак, разница в том, что
ConvertAll
метод можно использовать только в списке, и он возвращает список.Select
Метод может быть использован в любой коллекции , которая реализуетIEnumerable<T>
интерфейс, и он возвращаетIEnumerable<T>
.Кроме того, они по-разному выполняют обработку, поэтому в разных ситуациях у них есть свои сильные стороны. В
ConvertAll
методе проходит через список и создает новый список за один раз, в то время какSelect
метод использует ленивое выполнение и обрабатывает только те элементы , как вам необходимо. Если вам не нужен весь элемент,Select
метод более эффективен. С другой стороны, послеConvertAll
возврата списка нет необходимости сохранять исходный список.источник
Select
.Первый ответ не должен быть принятым. Я бывший MVP Microsoft по C # 2007 года.
В отличие от принятого ответа,
ConvertAll
намного эффективнее, чем комбинацияSelect
иToList()
.Прежде всего, он
ConvertAll
работает строго быстрее и использует для этого минимальный объем памяти. То же, что и Array.ConvertAll vs Select и ToArray. Это было бы гораздо более очевидным с массивом большей длины или большим количеством вызовов внутри цикла.1)
ConvertAll
знает размер окончательного списка и избегает перераспределения базового массива.ToList
() будет изменять размер массива несколько раз.2)
ToList
будет выполнять более медленныеIEnumerable<>
вызовы интерфейса , в то время какConvertAll
будет проходить через базовый массив без дополнительных вызовов или проверок диапазона.3) Select создаст дополнительный
IEnumerable<T>
объект.источник
Я знаю, что это немного поздно, но я все же добавил, потому что это может быть полезно для других в будущем.
При использовании его в выражении запроса EntityFramework не рекомендуется использовать ConvertAll (), поскольку он оценивает выражение, а не оставляет его как выражение для использования в будущем. Это серьезно ухудшает производительность выполнения запросов к базе данных, так как перед вычислением окончательного выражения потребуется выполнить несколько вызовов.
источник
ConvertAll
это методList<T>
. К тому времени, когда у вас есть список, вы уже оценили свое выражение. Но вы правы - если не хотите все оценивать,Select
лучше.