Ошибки, баги, вопросы - страница 3610

 
Alexey Viktorov #:

Это совсем о другом. Вычисляться они могут в любом порядке, а вот складываться, согласно примера, только по правилам арифметики. Исключительно слева неправо…

Артём, вариант с переменной i будет выглядеть так:

Сначала переменная идентифицируется значением 2. Затем оператор *= говорит о том, что переменной надо присвоить значение умноженное себя на что-то. А там, в этом «что-то» присваивается новое значение и это новое значение умножается на это «что-то». То-есть само на себя.

А вот с j получается так:

Сначала идентификация значением 2. Затем 2 умножается на ……… и тут, можно сказать не идентификация, а присвоение нового значения переменной. 

А собственно, если будут другие вразумительные объяснения, я готов их принять безоговорочно…

Выражение в скобках должно считаться первым по мат.правилам?

Если так, то каков порядок расчёта, и при чём тут инициализирующее значение, которое в первую же очередь заменяется значением 5 ?

 
Artyom Trishkin #:

Выражение в скобках должно считаться первым по мат.правилам?

Если так, то каков порядок расчёта, и при чём тут инициализирующее значение, которое в первую же очередь заменяется значением 5 ?

Видимо я не смогу объяснить так, чтобы было понятно…

Вот смотри… Казалось бы переменной уже присвоено новое значение, ан нет, пока ещё j равна 2


 
Alexey Viktorov #:

Видимо я не смогу объяснить так, чтобы было понятно…

Я прекрасно понял ход твоих мыслей.

Не понял какое участие в них имеет инициализирующее значение при условии, что оно сразу же должно заменяться значением 5

 
Alexey Viktorov #:
Вот смотри… Казалось бы переменной уже присвоено новое значение, ан нет, пока ещё j равна 2

Именно. Почему?

 
Artyom Trishkin #:

Именно. Почему?

Наверное потому, что присвоение нового значения происходит в момент использования. Или вообще присвоение не происходит в таком случае… ХЗ означает, я тоже Хотел бы Знать…

 
Alexey Viktorov #:
я тоже Хотел бы Знать…
+
 
Alexey Viktorov # :

Наверное потому, что присвоение нового значения происходит в момент использования. Или вообще присвоение не происходит в таком случае… ХЗ означает, я тоже Хотел бы Знать…

Я дал объяснение, но вы его не поняли.
 
Alain Verleyen #:
Я дал объяснение, но вы его не поняли.

Из Вашего пояснения видно, что последовательность расчётов никак не регламентируется, а отдаётся на "откуп" компилятору.

Но в обсуждаемом примере чётко прослеживается последовательность, где можно (а может и нужно) учитывать математические приоритеты. Иначе нет возможности понимать в какой из очередных компиляций приоритеты будут расставлены иначе, чем в предыдущий раз, что приведёт к совершенно иным результатам при работе программы.

Я понимаю, что можно все расчёты сделать построчно шаг за шагом. Но оно стоит того?

 
Artyom Trishkin # :

Из Вашего пояснения видно, что последовательность расчётов никак не регламентируется, а отдаётся на "откуп" компилятору.

Но в обсуждаемом примере чётко прослеживается последовательность, где можно (а может и нужно) учитывать математические приоритеты. Иначе нет возможности понимать в какой из очередных компиляций приоритеты будут расставлены иначе, чем в предыдущий раз, что приведёт к совершенно иным результатам при работе программы.

Я понимаю, что можно все расчёты сделать построчно шаг за шагом. Но оно стоит того?

Может быть, я что-то упустил из-за перевода. Я перечитаю.
 

MQL использует ту же компиляцию, что и язык C.

        push    rbp
        mov     rbp, rsp
        sub     rsp, 16 
        mov     dword ptr [rbp - 4 ], 0
        mov     dword ptr [rbp - 8 ], 2               j=2 
        mov     eax, dword ptr [rbp - 8 ]             temp=j
        mov     dword ptr [rbp - 8 ], 5               j=5 
        imul    eax, eax, 5                           temp=temp*5   //[2*5] 
        mov     dword ptr [rbp - 8 ], eax             j=temp 
        mov     esi, dword ptr [rbp - 8 ]
        mov     rdi, qword ptr [rip + std::cout@GOTPCREL]
        call    std::ostream::operator<<( int )@PLT
        xor     eax, eax
        add     rsp, 16 
        pop     rbp
        ret
Компиляция MSVC/GCC (которая дает j=25):
        push    rbp
        mov     rbp, rsp
        sub     rsp, 16
        mov     DWORD PTR [rbp- 4 ], 2                 j= 2 
        mov     DWORD PTR [rbp- 4 ], 5                 j= 5 
        mov     eax, DWORD PTR [rbp- 4 ]               temp=j
        imul    eax, eax                               temp=temp*temp //[ 5 * 5 ]
        mov     DWORD PTR [rbp- 4 ], eax               j=temp         //[ 25 ]
        mov     eax, DWORD PTR [rbp- 4 ]
        mov     esi, eax
        mov     edi, OFFSET FLAT:std::cout
        call    std::basic_ostream<char, std::char_traits<char> >::operator<<( int )
        mov     eax, 0 
        leave
        ret

Оба варианта верны.

Вы НЕ МОЖЕТЕ полагаться на порядок выполнения или на то, как компилятор будет оценивать операнды.