Рассмотрим этот код:
void foo()
{
goto bar;
int x = 0;
bar: ;
}
GCC и Clang отклоняют это , потому что переход к bar:
обходу инициализации переменной. MSVC вообще не жалуется (кроме случаев, x
когда bar:
вызывает предупреждение).
Мы можем сделать аналогичную вещь с switch
:
void foo()
{
switch (0)
{
int x = 0;
case 0: ;
}
}
Теперь все три компилятора выдают ошибки .
Эти фрагменты плохо сформированы? Или они вызывают UB?
Раньше я думал, что оба были плохо сформированы, но я не могу найти соответствующие части стандарта. [stmt.goto] ничего не говорит об этом, как и [stmt.select] .
c++
language-lawyer
goto
initializer
variable-declaration
HolyBlackCat
источник
источник
x
после прыжка./permissive-
флаг в MSVC, и он также будет жаловаться. Однако я не знаю, является ли поведение MSVC без этого флага четко определенным (я бы предположил, иначе, почему они это допустили?).Ответы:
Он плохо сформирован, когда инициализация не пустая.
Инициализатор делает инициализацию незаполненной. В отличие от этого
будет хорошо сформирован. Хотя обычные предостережения об использовании
x
с неопределенным значением будут применяться.источник
Из заявления goto :
источник