Каково полное “для” синтаксиса цикла в C?

59
задан jww 26 December 2018 в 00:24
поделиться

5 ответов

Запятая не эксклюзивна из для циклов; это - оператор запятой.

x = (a, b);

сделает первый a, тогда b, затем установит x на значение b.

для синтаксиса:

for (init; condition; increment)
    ...

, Который является несколько (игнорирующий continue и break на данный момент) эквивалентен:

init;
while (condition) {
    ...
    increment;
}

, Таким образом, Ваш для примера цикла (снова игнорирование continue и break) эквивалентен [1 136]

p=0;
while (p+=(a&1)*b,a!=1) {
    ...
    a>>=1,b<<=1;
}

, Который действует, как будто это было (снова игнорирование continue и break):

p=0; 
while (true) {
    p+=(a&1)*b;
    if (a == 1) break;
    ...
    a>>=1;
    b<<=1;
}

Две дополнительных детали для цикла, которые не были в упрощенном преобразовании в некоторое время цикл выше:

  • , Если условие опущено, это всегда true (приводящий к бесконечному циклу, если break, goto, или что-то еще не повреждает цикл).
  • А continue действия, как будто это был goto к маркировке незадолго до инкремента, в отличие от этого, continue в цикле с условием продолжения, который пропустит инкремент.

кроме того, важная деталь об операторе запятой: это - точка последовательности, как [1 121] и || (который является, почему я могу разделить его в отдельных операторах и сохранить его значение в целости).

<час>

Изменения в C99

стандарт C99 представляет несколько нюансов, не упомянутых ранее в этом объяснении (который очень хорош для C89/C90).

Первый, все циклы являются блоками самостоятельно. Эффективно,

for (...) { ... }

самостоятельно обертывается в пару фигурных скобок

{
for (...) { ... }
}

стандарт sayeth:

Операторы цикла ISO/IEC 9899:1999 В§6.8.5

В¶5 оператор цикла является блоком, объемом которого является строгое подмножество объема его блока включения. Тело цикла является также блоком, объемом которого является строгое подмножество объема оператора цикла.

Это также описано в Объяснении с точки зрения дополнительного набора фигурных скобок.

, Во-вторых, init часть в C99 может быть (единственным) объявлением, как в [1 146]

for (int i = 0; i < sizeof(something); i++) { ... }

Теперь, 'блок повторился, цикл' добивается признания; это объясняет, почему к переменной i нельзя получить доступ вне цикла. Можно объявить больше чем одну переменную, но они должны все иметь тот же тип:

for (int i = 0, j = sizeof(something); i < j; i++, j--) { ... }

стандарт sayeth:

ISO/IEC 9899:1999 В§6.8.5.3 для оператора

оператор

for ( clause-1 ; expression-2 ; expression-3 ) statement

ведет себя следующим образом: выражение 2 выражения является выражением управления, которое оценено перед каждым выполнением тела цикла. Выражение 3 выражения оценено как пустое выражение после каждого выполнения тела цикла. Выражение if 1 является объявлением, объемом любых переменных, которые это объявляет, является остаток от объявления и всего цикла, включая другие два выражения; это достигнуто в порядке выполнения перед первой оценкой выражения управления. Выражение if 1 является выражением, оно оценено как пустое выражение перед первой оценкой выражения управления. <глоток> 133)

И пункт 1 и выражение 3 могут быть опущены. Опущенное выражение 2 заменяется ненулевой константой.

<глоток> 133) Таким образом, пункт 1 определяет инициализацию для цикла, возможно объявляя одну или несколько переменных для использования в цикле; выражение управления, выражение 2, определяет оценку, сделанную перед каждым повторением, таким, что выполнение цикла продолжается, пока выражение не выдерживает сравнение равный 0; и выражение 3 определяет операцию (такую как постепенное увеличение), который выполняется после каждого повторения.

131
ответ дан Solomon Slow 24 November 2019 в 18:10
поделиться

Запятая просто разделяет два выражения и допустима где угодно в C, где нормальное выражение позволяется. Они выполняются в порядке слева направо. Значение самого правого выражения является значением полного выражения.

for циклы состоят из трех частей, любая из которых может также быть пустой; один (первое) выполняется вначале, и одно (третье) в конце каждого повторения. Эти части обычно инициализируют и увеличивают счетчик, соответственно; но они могут сделать что-либо.

вторая часть тест , который выполняется в начале каждого выполнения. Если тест уступает false, цикл прерывается. Вот и все.

8
ответ дан Konrad Rudolph 24 November 2019 в 18:10
поделиться

Стиль C для цикла состоит из трех выражений:

for (initializer; condition; counter) statement_or_statement_block;
  • инициализатор работает однажды, когда цикл запускается.
  • условие проверяется перед каждым повторением. Цикл работает как долго, он оценивает к истинному.
  • счетчик работает однажды за каждым повторением.

Каждая из этих частей может быть выражением, допустимым на языке, в котором Вы пишете цикл. Это означает, что они могут использоваться более творчески. Что-либо, что Вы хотите сделать заранее, может войти в инициализатор, что-либо, что Вы хотите сделать промежуточный, может войти в условие или счетчик, до точки, где цикл больше не имеет никакого тела.

Для достижения этого оператор запятой входит очень удобный. Это позволяет Вам цепочечным выражениям вместе формировать единственное новое выражение. Большую часть времени это используется тот путь в для цикла, другие последствия оператора запятой (например, соображения присвоения значения) играют второстепенную роль.

Даже при том, что можно сделать умные вещи при помощи синтаксиса творчески - я избежал бы его, пока я не нахожу действительно серьезное основание сделать так. Играть в гольф кода с для циклов делает код тяжелее, чтобы считать и понять (и поддержать).

Википедия имеет хорошее статья о для цикла также.

5
ответ дан Tomalak 24 November 2019 в 18:10
поделиться

Все является дополнительным в for цикл. Мы можем инициализировать больше чем одну переменную, мы можем проверить больше чем на одно условие, мы можем выполнить итерации больше чем одной переменной с помощью оператора запятой.

следующий for цикл возьмет Вас в бесконечный цикл. Будьте осторожны путем проверки условия.

for(;;) 
2
ответ дан GEOCHET 24 November 2019 в 18:10
поделиться

Конрад упомянул ключевой момент, который я хотел бы повторить: значение самого правого выражения - это значение всего выражения.

Компилятор Gnu сообщил об этом предупреждении, когда я поместил два теста в раздел «условие» цикла for

warning: left-hand operand of comma expression has no effect

На самом деле я имел в виду два теста с символом «&&» между ними. По утверждению Конрада, только тест справа от запятой повлияет на состояние.

0
ответ дан 24 November 2019 в 18:10
поделиться
Другие вопросы по тегам:

Похожие вопросы: