1. Пользуйтесь тегами кода. - [code] ... [/code]
2. Точно указывайте язык, название и версию компилятора (интерпретатора).
3. Название темы должно быть информативным.
В описании темы указываем язык!!!
| sheka |
7.10.2011 22:44
Сообщение
#1
|
![]() Я. ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 809 Пол: Мужской Реальное имя: Саша Репутация: 11 |
pow() некорректно работает если используется инкремент или декремент в его параметрах.
Задание: Совершая обход так: 1 3 4 10 2 5 9 11 6 8 12 15 7 13 14 16 заполнить матрицу а такими значениями: b11b12...bnn Kod (Показать/Скрыть)
В таком исполнении pow(b[k++ / N], k % N + 1); работает так как надо (еще недавно и так не работал, но теперь почему-то работает): результат (Показать/Скрыть)
а в таком pow(b[k / N], ++k % N + 1); - нет: результат (Показать/Скрыть)
Сообщение отредактировано: sheka - 8.10.2011 0:02 |
![]() ![]() |
| IUnknown |
8.10.2011 22:27
Сообщение
#2
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: 627 |
Цитата Компилятор GNU GCC (CodeBlocks 10.05) ничего не выдает. Неправда. Зайди в Project -> Build Options, в Compiler Flags включи "Enable all compiler warnings" (которая -Wall), и пересобери проект. Можешь узнать очень много интересного Теперь по while (i < M && 0 <= j) a[i++][j--] = pow(b[k / N], (++k) % N + 1);, что будет выполнено раньше, вычисление первого параметра со старым значением k, а потом инкремент и вычисление второго параметра с новым значением, или наоборот, сначала значение k инкрементируется, и вычислится второй параметр для pow(), а потом с той, уже увеличенной k, будет вычисляться первый параметр - не может никто. Это компиляторозависимо, и, кроме всего прочего, зависит от оптимизатора, ибо в конечном счете он выбирает, в каком порядке вычислять параметры, чтоб было как можно оптимальней. А это уже неопределенное поведение со всеми вытекающими последствиями: нестабильная работа программы (ты ж сам говорил, что раньше не работало, теперь вдруг заработало, помнишь? Явный признак, что что-то не так), и предупреждение, выдаваемое компилятором. Кстати, с первым вариантом: while (i < M && 0 <= j) a[i++][j--] = pow(b[k++ / N], k % N + 1);- абсолютно та же история, побочный эффект присутствует и там, а что если сначала вычислится второй параметр, а только потом - первый? Упс... Опять перестанет работать... Для гарантированного порядка вычисления - используй временные переменные, тогда UB не будет. Кстати, разницу между префиксным и постфиксным ++ (да и -- тоже) знаешь? Сообщение отредактировано: IUnknown - 8.10.2011 22:28 |
sheka pow() 7.10.2011 22:44
IUnknown Главное, ничего не сказал, в чем корявость, что не... 7.10.2011 22:55
sheka Исправил. 8.10.2011 0:01
IUnknown Ты на самом деле думаешь, что оба эти фрагмента де... 8.10.2011 1:23
TarasBer Я бы вообще запретил ++ в составе сложных выражени... 8.10.2011 18:27
sheka Хм, я как бы понимаю, что вначале значение пропус... 8.10.2011 22:05
Lapp Но я думал что в этом виноват pow, и никак не ++.... 9.10.2011 6:42
TarasBer
Объясните, пожалуйста, что делает ++ ужасного.
h... 9.10.2011 13:52
sheka Volvo,
Вычисление логических выражений по коротко... 13.10.2011 16:48
IUnknown Я не про вычисление логических выражений. Я про
in... 13.10.2011 17:28![]() ![]() |
|
Текстовая версия | 13.12.2025 9:14 |