Действительность принудительной, по крайней мере, одной итерации цикла for с операцией goto
Отказ от ответственности: я знаю, что это неясно, и я не буду так программировать. Я знаю предпочтительный оператор do-while
, а не тот, вопрос о достоверности конкретной языковой конструкции.
Является ли goto
всегда предполагаемым, чтобы опустить условное выражение цикла for
? Из того, что я наблюдал, он пропускает как первые (то есть инициализирующие), так и вторые выражения. Будет ли это всегда происходить таким образом или это поведение зависит исключительно от компилятора?
#include <stdio.h>
int main(void)
{
int m = 5;
goto BODY;
for (m = 0; m < 5; m++)
BODY: puts("Message"); // prints "Message" once
printf("m = %d\n", m); // prints m = 6
return 0;
}
Ответы
Ответ 1
Да, вы перепрыгиваете через m = 0
и m < 5
, и это так, как должно быть.
for (A; B; C)
D;
эквивалентно
{
A;
loop:
if (B)
{
D;
C;
goto loop;
}
}
Нет способа передать управление в точку между A
и B
.
Семантика вашего цикла точно такая же, как и эта версия "pure goto":
int m = 5;
goto BODY;
m = 0;
loop:
if (m < 5)
{
BODY: puts("Message"); // prints "Message" once
m++;
goto loop;
}
printf("m = %d\n", m); // prints m = 6
Ответ 2
Предполагается, что goto всегда должен опускать условное выражение для цикл?
Да. Переход goto всегда является безусловным прыжком, и выполнение будет нести от метки оттуда.
Из проекта C11, § 6.8.6.1 Операция goto:
Оператор goto вызывает безусловный переход к выражению с префиксом названной метки в прилагаемой функции.
За исключением исключения:
Идентификатор в инструкции goto должен обозначать метку, расположенную где-то в закрывающей функции. Операция goto не должна прыгать из-за пределов идентификатора, имеющего измененный введите внутри области этого идентификатора.
Ответ 3
Оператор goto
в вашем коде вызывает безусловный переход к выражению внутри цикла for
. Когда этот оператор выполняется, поток программы должен зависеть от условного выражения в цикле. Итак, да, инициализация внутри цикла пропущена.
Ответ 4
Вы должны использовать цикл do/while
, например, если для цикла есть следующее:
for(A ; B ; C)
{
D;
}
Вы должны использовать следующий цикл do/while:
A;
do
{
D;
C;
}while(B);
который заставит первую итерацию.
ИЗМЕНИТЬ
См. комментарий от chux: Если D;
содержит continue
, этот способ не будет работать, вам понадобится другой способ
EDIT II
Когда вопрос был отредактирован, этот ответ больше не является прямым ответом на вопрос, но я не буду его удалять, поскольку он может помочь кому-то...
Ответ 5
Оператор goto в программировании на C обеспечивает безусловный переход от 'goto' к помеченному выражению в той же функции.
Обратите внимание на безусловный здесь.
так что да, предполагается, что оно не допускает условного выражения цикла for
.
Ответ 6
Это совершенно законно в c. Нет ничего плохого в переходе в цикл for, если вы не пропустите какие-либо объявления или инициализации автоматических переменных.
В этом случае m увеличивается один раз, и цикл завершается из-за выполнения условия остановки.