на самом деле меня тоже сперва смутило) правда я не любитель писать стихи посредством кода, поскольку зачастую чревато багами и в общем - хреновой читабельностью, однако и тут есть некоторый кураж) фишка в том что компилеры визуала и билдера генерят код примерно такой: Code: i=5; i++; i++; i+=i; что вполне справедливо для компилятора использующего одну ячейку памяти (под i конечно) и в чем впрочем можно убедиться взяв асм листинг. Code: .text:00401000 push ebp .text:00401001 mov ebp, esp .text:00401003 push ecx .text:00401004 mov [ebp+i], 5 ; i=5 .text:0040100B mov eax, [ebp+i] .text:0040100E add eax, 1 .text:00401011 mov [ebp+i], eax ; i++; i==6 .text:00401014 mov ecx, [ebp+i] .text:00401017 add ecx, 1 .text:0040101A mov [ebp+i], ecx ; i++; i==7 .text:0040101D mov edx, [ebp+i] .text:00401020 add edx, [ebp+i] .text:00401023 mov [ebp+i], edx ; i += i; i==7+7==14 .text:00401026 mov eax, [ebp+i] .text:00401029 push eax .text:0040102A push offset Format ; "%d" .text:0040102F call ds:__imp__printf
а я сперва посчитал 13)) видать отвык) но слева то другой вопрос. приоритеты операций везде одинаковые, но ++i виртуалка сохраняет как одно значение, а еще ++i - как еще одно. и они то и складываются.
нe очeвидно. стaндaрт в тaких случaях ничeго нe гaрaнтируeт и рaзныe компили будут гeнeрить рaзный код.
Есть такая тема - порядок операторов. Нашёл ссылки с порядком операторов. C# C++ У C++ и C# они отличаются. У C++ префиксный ++ выше +, а в C# они на одном уровне. Вот и разгадка. Нет, ошибся и окончательно запутался.
кому интересно, на васме весьма живо обсуждали эту тему. http://wasm.ru/forum/viewtopic.php?id=20504&p=1
да вот не соглашусь, иначе какой код компилеру генерить if(random()) // + else // ++ на самом деле префиксный инкремент и в сях и в шарпе имеет приоритет выше чем аддитивные операторы.
да не, по сути все верно - вопрос в памяти. если добавить вторую переменную, например, то мы и получим 13, аля как это срабатывает в манагед-коде. proof of concept: int y, i = 5; y = ++i; i = y + ++i; printf("%d", i); результат == 13 просто за счет того что i не переписывается дважды.
В пределах двух точек следования переменная не должна меняться более одного раза, иначе неопределенное поведение гарантировано) Это я о С++ i = ++i + ++i; тут i меняется три раза, вместо положенного одного
i является стековой переменной. в листинге под нее место выделяется за счет push ebx, далее [ebp-4] является указателем на нее. разбирая выражение i = ++i + ++i в хронологическом порядке, получаем что выполняем первый инкремент, [ebp-4] увеличивается на единицу. второй инкремент - опять тоже самое происходит. ну и наконец суммируем результат - тк хранится она у нас в одном месте, то и получаем вполне обоснованный результат)
проверил на всех компилях, что у меня есть. везде 14. но это не значит, что результат определен. может быть и другой результат, нужно только хорошенечко потестить на всем, чем только можно
думаю 12, ща проверю ооо вот это уже ништяк))))))))))) при конфиге прожекта Release если отключить все оптимизации компилятора получаем 12, если выбрать быстрый код - 11 (VS2010)