Новые сообщения [новые:0]
Дайджест
Горячие темы
Избранное [новые:0]
Форумы
Пользователи
Статистика
Статистика нагрузки
Мод. лог
Поиск
|
31.05.2014, 18:18
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
Есть код: Код: c# 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34.
Почему при выводе на экран item.Property не равно 777?! ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 18:28
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
Lamo2012, foreach создает копию итератора для перечисления, не желательно вообще проводить такие манипуляции и удаления итемов в For Each ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 18:40
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
Lamo2012, всё дело в этой строке Код: c# 1.
list2 имеет тип IEnumerable<MyClass> и так как ты в Select создаешь новый экзмепляр list, то при выполнении foreach каждый раз создаются новые - временные - экземпляры MyClass. Чтобы получить ожидаемое поведение нужно превратить временную коллекцию в постоянную с помощью ToList()/ToArray Код: c# 1.
или убрать создание копии MyList: Код: c# 1.
... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 18:41
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
хотя возможно вру.... ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 21:18
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
bazile... Чтобы получить ожидаемое поведение нужно превратить временную коллекцию в постоянную с помощью ToList()/ToArray Спасибо, помогло. Я наивно думал что foreach просто вызовет отложенное выполнение list.Select(x => new MyClass { Id = x.Id, Property = x.Property }) и присвоение его list2 а потом переберет list2 и присвоит нужные значения свойству. Но вот копирование содержимого списка это для меня сюрприз. Зачем он это делает?! ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 22:23
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
Lamo2012, автор Я наивно думал что foreach просто вызовет отложенное выполнение list.Select(x => new MyClass { Id = x.Id, Property = x.Property }) он просто и вызывает. авторНо вот копирование содержимого списка это для меня сюрприз. Зачем он это делает?! где вы увидели копирование ? попробуйте указать явно тип переменной list2 в коде, а не прикрываться что компилятор выведет,( он то знает все) а после этого посмотреть что это за тип в справке, и как он работает.. ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 22:31
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
Lamo2012 Но вот копирование содержимого списка это для меня сюрприз. Зачем он это делает?! Потому что нету никакого списка. Есть IEnumerable<T>. У которого foreach дергает GetEnumerator<T>. Который честным образом выполняет x => new MyClass, т.е и создает копию. Сколько раз foreach, столько раз GetEnumerator, столько и копий. ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 22:57
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
zz,авторт.е и создает копию. скорее создают объект на основе данных другого объекта, ( то что типы объектов совпадают, чистая случайность автора кода) копирование тут как бы не уместно, вообще как бы надо поосторожней с терминами, я вот в соседнем топике рассмотрел локальные переменные с точки зрения стека, а ведь это не прально, 90 процентов диезников и не знает что это, да и ненужно это им, тут как бы другое определение локальных переменных надо ( более народное) ... |
|||
:
Нравится:
Не нравится:
|
|||
|
31.05.2014, 23:16
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
VSVLAD, авторне желательно вообще проводить такие манипуляции и удаления итемов в For Each врете )) природа переменной итерации readonly ... |
|||
:
Нравится:
Не нравится:
|
|||
|
01.06.2014, 08:55
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
zz...Есть IEnumerable<T>. У которого foreach дергает GetEnumerator<T>. Который честным образом выполняет x => new MyClass, т.е и создает копию. Сколько раз foreach, столько раз GetEnumerator, столько и копий. Т.е. получается я сам себя ввел в заблуждение именами своих переменных. В list2 у меня совсем не лист, а дерево выражений (так оно правильно вроде называется), которое выполняется при каждом foreach, честно создавая мне все новые копии айтемов исходного list. Я правильно понял? ... |
|||
:
Нравится:
Не нравится:
|
|||
|
01.06.2014, 21:33
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
Lamo2012, Деревья выражений строятся для IQueryable) У вас там IEnumerable обертка, итератор которой для каждого элемента вызывает вот эту ф-ию: x => new MyClass { Id = x.Id, Property = x.Property } ... |
|||
:
Нравится:
Не нравится:
|
|||
|
02.06.2014, 10:14
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
Lamo2012В list2 у меня совсем не лист, а дерево выражений (так оно правильно вроде называется), которое выполняется при каждом foreach, честно создавая мне все новые копии айтемов исходного list. Я правильно понял? У Вас какая-то путаница с понятиями. Изначально имеет list1 с типом List<MyClass>. Поскольку List<MyClass> реализует интерфейс IEnumerable<MyClass>, у него есть метод GetEnumerator<MyClass>, который возвращает итератор по объекту list1. Далее Вы вот этим выражением var list2 = list.Select(x => new MyClass { Id = x.Id, Property = x.Property }); создали объект IEnumerable<MyClass> с измененным , по отношению к list, итератором. Что же изменилось в этом итераторе? Изменился метод MoveNext, который стал звучать примерно так: "При запросе следующего элемента последовательности верни мне, пожалуйста, новый экземпляр MyClass". Эта инструкция зафиксирована в качестве параметра метода Select, и она является лямбда-выражением (но не деревом выражений). Дерево выражений было бы параметром метода Select, если бы он относился к объекту типа IQueryable, как уже справедливо отметили выше. Вас, скорее всего, смущает "ленивость" происходящих операций, дескать - а почему преобразование выполняется не "мгновенно", а отложенно. А потому, что оно не должно выполняться. Грубо говоря, Вы меняете закон получения последовательности. А выполняется этот закон в момент перебора последовательности. Можно "зафиксировать" этот закон, выполнив метод ToList(), про что тоже уже говорили выше. ... |
|||
:
Нравится:
Не нравится:
|
|||
|
02.06.2014, 11:36
|
|||
---|---|---|---|
|
|||
присвоение внутри foreach |
|||
#18+
zz, авторУ Вас какая-то путаница с понятиями Проблема не нова, я думаю процентов 50 не вкуривают что это такое, я ( честно) встречал руководителей проектов, которые так и представляли что перчисление это указатель на кучу где лежит какая то последовательность, и публично это оспаривали, а на мой аргумент автор while (true) { yield return 1000; } говорили что так делать нельзя ( не хватит памяти у компьютера...), и что интересно, они справлялись со своей задачей и делали балоемкие проекты..., так что имхо одно другому не мешает, особенно в ASP.net. >Lamo2012 Lamo2012 новые копии айтемов исходного list. Вот это как серпом по яицам, ну если копия докажите что o1 копия o2, ... |
|||
:
Нравится:
Не нравится:
|
|||
|
02.06.2014, 14:18
|
|||
---|---|---|---|
присвоение внутри foreach |
|||
#18+
zz, и чем ваша простыня сильно отличается от моего предложения? я в курсе, что логика находится в итераторе, основной посыл сообщения был в том, что для списков не строятся деревья выражений. zzВас, скорее всего, смущает "ленивость" происходящих операций, дескать - а почему преобразование выполняется не "мгновенно", а отложенно. Меня она совершенно не смущает и никогда не смущала. А должна? ... |
|||
:
Нравится:
Не нравится:
|
|||
|
|
start [/forum/topic.php?fid=20&mobile=1&tid=1402858]: |
0ms |
get settings: |
9ms |
get forum list: |
14ms |
check forum access: |
4ms |
check topic access: |
4ms |
track hit: |
55ms |
get topic data: |
11ms |
get forum data: |
2ms |
get page messages: |
51ms |
get tp. blocked users: |
4ms |
others: | 15ms |
total: | 169ms |
0 / 0 |