Здравствуйте, abc1234573, Вы писали:
A>что возвращает выражение типа. когда одно значение присваивается другому
A>int a, b = 1;
A>if (a = b) // именно здесь что возвращает выражение? A>{ A> // print result A>}
Возварщает значение а.
Все это хорошо видно в дизассемблере, например, в студии:
if( a = b )
009D14D5 mov eax,dword ptr [b]
009D14D8 mov dword ptr [a],eax
009D14DB cmp dword ptr [a],0
009D14DF je main+48h (9D14F8h)
Здравствуйте, abdab, Вы писали:
A>>что возвращает выражение типа. когда одно значение присваивается другому
A>>if (a = b)
A>Возварщает значение а. A>Все это хорошо видно в дизассемблере, например, в студии:
Ссылаться надо не на дизассемблер, а на стандарт языка.
Здравствуйте, Centaur, Вы писали:
C>Здравствуйте, abdab, Вы писали:
A>>>что возвращает выражение типа. когда одно значение присваивается другому
A>>>if (a = b)
A>>Возварщает значение а. A>>Все это хорошо видно в дизассемблере, например, в студии:
C>Ссылаться надо не на дизассемблер, а на стандарт языка.
Правда ваша, но все же мне кажется, что в таких простейших вопросах можно и самому на практике попытаться их разрешить, при этом будешь знать не только ответ на свой вопрос, но и увидишь во что реально компилятор превращает этот код.
Здравствуйте, Centaur, Вы писали:
C>Здравствуйте, abdab, Вы писали:
A>>>что возвращает выражение типа. когда одно значение присваивается другому
A>>>if (a = b)
A>>Возварщает значение а. A>>Все это хорошо видно в дизассемблере, например, в студии:
C>Ссылаться надо не на дизассемблер, а на стандарт языка.
Лень искать копию стандарта, так что на память:
1. Конструкция if определена как if (выражение)
2. Выражение истино, если отлично от нуля. Если выражение равно нулю оно ложно.
3. a = b, a = b = c = d, a < b == c < d, function(a, b) и все остальное, что возвращает значение (и на первый взгляд не возвращает — тоже) — являеться выражением. (В стандарте правдо от противного, сказано что выражения и как могут образовываться. Но там это кусок здоровый)
3.1 Выражение может быть простым — константа, строка, функция
3.2 Выражение может быть составным — последовательность операций над выражениями
3.3 Любое выражение имеет значение — простое понятно что за значение, составное выражение — это результат последний по приоритету операции
4. Выражение от a = b: составное выражение языка. Результат выражения (3.3) результат последней по приоритету операции (здесь она одна "="). Результат операции "=" — все что справо.
Т.е. у выражения a = b — есть 2 результата: изменение a и все что справа от "=".
При { a = b; } второй результат не используеться (его нет), при { if ( a = b ) ; } — второй результат (значение а в данном контексте) и проверяеться на равенство нулю.
Мораль сей сказки такова:
1. В си можно пихать вычисления куда захочеться, ну типа: if ( a = b — 8, b = a + 185, c = a * b) — откампилить и будет славно работать.
2. Так лучше не делать. Ну или знать рамки разумного.
3. Стоит прочесть книгу Кернитигана и Ричи, что бы непонятные конструкции стали чертовски удобной фичей. Которой все равно см. пункт 2.
4. результат выражения — lvalue — это то что слева, в соответствии с приоритетом операций (как самые простые примеры):
4.1 if (a) — выражение от а — это само а. Если а не равно нулю — значит истина, иначе ложь.
4.2 if (a = b) — выражение преравнивания — результат выражение все что справо (значение b), этому приравниваеться все что слева (переменная а) и это (значение b) используеться как критерий истиности — равно ли нулю.
4.3 if (a = b == b) — составное выражение. Вычсляеться в соответствии с приоритетом операций — сначала приравнивание (a = b == b) --> ( (a = b) == b) --> ( a == b ). Вычисляеться операция сравнения a (ужо приравненого значению b) и b. Если они равны — то 1 (выражение истино) иначе ноль
Здравствуйте, 11molniev, Вы писали:
1>4.3 if (a = b == b) — составное выражение. Вычсляеться в соответствии с приоритетом операций — сначала приравнивание (a = b == b) --> ( (a = b) == b) --> ( a == b ). Вычисляеться операция сравнения a (ужо приравненого значению b) и b. Если они равны — то 1 (выражение истино) иначе ноль
сначала проверка равенства, потом присваивание:
a = b == c <=> a = (b == c)
Здравствуйте, abdab, Вы писали:
C>>Ссылаться надо не на дизассемблер, а на стандарт языка.
A>Правда ваша, но все же мне кажется, что в таких простейших вопросах можно и самому на практике попытаться их разрешить, при этом будешь знать не только ответ на свой вопрос, но и увидишь во что реально компилятор превращает этот код.
Дизассемблер может быть полезен в исследовании того, насколько данный компилятор соответствует стандарту.
Строить же индукцию о языковых правилах на основании конкретного дизассемблера -- опасное и бесполезное занятие.