"++ l * = m" неопределенное поведение? - PullRequest
16 голосов
/ 02 декабря 2010

Я начал изучать C ++ 0x.Я где-то встречал следующее выражение:

int l = 1, m=2;
++l *= m;

Я понятия не имею, имеет ли второе выражение хорошо определенное поведение или нет.Поэтому я спрашиваю это здесь.

Разве это не UB?Я просто хочу знать.

Ответы [ 2 ]

14 голосов
/ 02 декабря 2010

Выражение хорошо определено в C ++ 0x.Prasoon здесь .

предлагает очень часто задаваемые вопросы по стандартным цитатам. Я не уверен, что такое высокое соотношение (буквальные цитаты стандартов: пояснительный текст) предпочтительнееИтак, я даю дополнительное небольшое объяснение: помните, что ++L эквивалентно L += 1, и что вычисление значения этого выражения секвенируется после приращения L.И в a *= b вычисление значения выражения a секвенируется до присвоения результата умножения в a.

Какие у вас побочные эффекты?

  • Увеличение
  • Присвоение результата умножения

Оба побочных эффекта транзитивно секвенированывышеуказанными двумя последовательностями после и последовательностями до .

3 голосов
/ 02 декабря 2010

В приведенном выше коде префикс ++ имеет приоритет над *= и поэтому выполняется первым. В результате l равно 4.

ОБНОВЛЕНИЕ: Это действительно неопределенное поведение. Мое предположение о том, что правящий приоритет был ложным.

Причина в том, что l является одновременно lvalue и rvalue в *=, а также в ++. Эти две операции не являются последовательными. Следовательно, l пишется (и читается) дважды "без точки последовательности" (старая стандартная формулировка), и поведение не определено.

Как примечание, я предполагаю, что ваш вопрос связан с изменениями, касающимися точек последовательности в C ++ 0x. C ++ 0x изменил формулировку, касающуюся «точек последовательности», на «последовательность перед», чтобы сделать стандарт более понятным. Насколько мне известно, это не меняет поведение C ++.

ОБНОВЛЕНИЕ 2: Оказывается, на самом деле есть четко определенная последовательность в соответствии с разделами 5.17 (1), 5.17 (7) и 5.3.2 (1) проекта N3126 для C ++ 0x . @ Йоханнес Шауб ответ правильный и документирует последовательность заявления. Кредит должен, конечно, пойти на его ответ.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...