Все они имеют неопределенное поведение до C ++ 17 и все имеют четко определенное поведение после C ++ 17.
Обратите внимание, что вы не модифицируете i
больше, чем один раз в любом примере. Вы изменяете его только с приращением.
Тем не менее, это также неопределенное поведение - иметь побочный эффект на одном скаляре (здесь приращение i
) без последовательности с вычислением значения (здесь слева - ручное использование i
). Независимо от того, вызван ли побочный эффект непосредственным воздействием на переменную, или с помощью ссылки, или указателя, не имеет значения.
До C ++ 17 оператор <<
не подразумевал какой-либо последовательности своих операндов, поэтому поведение не определено во всех ваших примерах.
Начиная с C ++ 17, оператор <<
гарантированно оценивает свои операнды слева направо. C ++ 17 также расширил правила последовательности операторов для перегруженных операторов при вызове с нотацией оператора. Таким образом, во всех ваших примерах поведение четко определено, и левостороннее использование i
оценивается first , перед тем как значение i
увеличивается.
Обратите внимание, однако, что некоторые компиляторы не внедрили эти изменения в правила оценки очень своевременно, поэтому, даже если вы используете флаг -std=c++17
, он, к сожалению, может нарушать ожидаемое поведение в более старых и текущих версиях компилятора.
Кроме того По крайней мере, в случае G CC предупреждение -Wsequence-point
явно задокументировано, чтобы предупредить даже о поведении, которое стало четко определенным в C ++ 17, чтобы помочь пользователю избежать написания кода, который будет иметь неопределенное поведение в C и более ранние версии C ++, см. G CC документацию .
Компилятору не требуется (и он не может) диагностировать все случаи неопределенного поведения. В некоторых простых ситуациях он сможет дать вам предупреждение (которое вы можете превратить в ошибку, используя -Werror
или подобное), но в более сложных случаях это не так. Тем не менее, ваша программа потеряет любую гарантию на ее поведение, если у вас есть неопределенное поведение, с диагнозом или без.