Поскольку, по сравнению с в то время как в программировании C?

В C существует три цикла: for, while, и do-while. Каково различие между ними?

Например, это кажется почти всеми while операторы могут быть заменены for операторы, правильно? Затем что использует преимущество while?

74
задан Wil Moore III 12 October 2018 в 19:14
поделиться

16 ответов

Между for и while: while не требует ни инициализации, ни оператора обновления, поэтому он может выглядеть лучше, более элегантно; для может иметь отсутствующие операторы, один, два или все, поэтому это наиболее гибкий и очевидный вариант, если вам нужна инициализация, условие цикла и «обновление» перед циклом. Если вам нужно только условие цикла (проверено в начале цикла), то , а более элегантно.

Между for / while и do-while : в do-while условие оценивается в конце цикла. Удобнее, если цикл нужно выполнить хотя бы один раз.

2
ответ дан 24 November 2019 в 11:47
поделиться

Все они одинаковы в своей работе. Вы можете делать то же самое, используя любой из них. Но по удобочитаемости, удобству использования, удобству и т. Д. Они различаются.

2
ответ дан 24 November 2019 в 11:47
поделиться

Одна из особенностей do while заключается в том, что для завершения процесса вам необходимо поставить точку с запятой после while. Это часто используется в макроопределениях, чтобы выполнить несколько операторов только один раз, ограничивая при этом влияние макроса. Если макросы определены как блоки, могут возникать некоторые ошибки синтаксического анализа.

Одно из объяснений среди других

2
ответ дан 24 November 2019 в 11:47
поделиться

A for предлагают фиксированную итерацию с использованием индекса или варианты этой схемы.

A while и do... while - это конструкции, которые используются, когда есть условие, которое должно проверяться каждый раз (кроме некоторых конструкций, похожих на индекс, см. выше). Они различаются тем, когда выполняется первое выполнение проверки условия.

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

3
ответ дан 24 November 2019 в 11:47
поделиться

Разница между while и do-while заключается в том, что while проверяет условие цикла, и если оно истинно, выполняется тело, а условие проверяется снова. Do-while проверяет условие после выполнения тела, поэтому с do-while тело выполняется по крайней мере один раз.

Конечно, вы можете написать цикл while как do-while и vv, но это обычно требует некоторого дублирования кода.

2
ответ дан 24 November 2019 в 11:47
поделиться

Вы должны использовать такой цикл, который наиболее полно соответствует вашим потребностям. Например:

for(int i = 0; i < 10; i++)
{
    print(i);
}

//or

int i = 0;
while(i < 10)
{
    print(i);
    i++;
}

Очевидно, что в такой ситуации "for" выглядит лучше, чем "while". А "do while" следует использовать, когда некоторые операции должны быть выполнены еще до того момента, когда будет проверено условие цикла.

Извините за мой плохой английский).

4
ответ дан 24 November 2019 в 11:47
поделиться

Помните, что цикл for по сути представляет собой причудливый цикл while . Это одно и то же.

while <some condition is true> {
   // do some stuff
   // possibly do something to change the condition
}


for ( some var, <some condition is true>; increment var ) {

}

Преимущество цикла for в том, что его сложнее случайно создать бесконечный цикл. Или, скорее, это более очевидно, когда вы это делаете, потому что вы обычно помещаете цикл var в начальный оператор.

Цикл while более понятен, когда вы не выполняете стандартный шаблон увеличения. Например:

int x = 1;
while( x != 10 ) {
  if ( some condition )
     x = 10;
  else 
     x += 5;
}
5
ответ дан 24 November 2019 в 11:47
поделиться

Если вы хотите, чтобы цикл выполнялся, пока условие истинно, а не в течение определенного количества итераций, это гораздо легче понять другому:

while (cond_true)

чем что-то вроде этого:

for (; cond_true ; )
8
ответ дан 24 November 2019 в 11:47
поделиться

Они все взаимозаменяемы; вы могли бы выбрать один тип и использовать только его, но обычно один из них более удобен для данной задачи. Это как сказать: "Зачем нужен switch, можно просто использовать кучу операторов if" - верно, но если это обычный шаблон для проверки переменной на набор значений, то будет удобно и гораздо легче читать, если для этого есть языковая функция

.
10
ответ дан 24 November 2019 в 11:47
поделиться

Для удобства чтения

10
ответ дан 24 November 2019 в 11:47
поделиться

A цикл while всегда будет сначала оценивать условие.

while (condition) {
  //gets executed after condition is checked
}

Цикл do / while всегда будет выполняться код в сделать {} блок первым а затем оцените состояние.

do {
  //gets executed at least once
} while (condition); 

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

for (int x = 0; x < 100; x++) {
   //executed until x >= 100
}

В конце концов, все они по-прежнему являются циклами, но они предлагают некоторую гибкость в том, как они выполняются.

Вот отличное объяснение аргументов , стоящих за использованием каждого отдельного типа цикла, которое может помочь прояснить ситуацию. Спасибо clyfe

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


Циклы For особенно удобны, потому что они лаконичны. Чтобы этот цикл for

for (int x = 0; x < 100; x++) {
   //executed until x >= 100
}

был записан как цикл while, вам необходимо сделать следующее.

int count = 0;
while (count < 100) {
  //do stuff
  count++;
}

В этом случае есть еще кое-что, за чем нужно следить, и count ++; может потеряться в логике. Это может вызвать проблемы в зависимости от того, где count увеличивается, и от того, должно ли оно увеличиваться до или после логики цикла. В цикле for ваша переменная счетчика всегда увеличивается перед следующей итерацией цикла, что добавляет единообразия вашему коду.


Для полноты, вероятно, имеет смысл поговорить об операторах break и continue , которые пригодятся при обработке цикла.

break немедленно завершит текущий цикл, и больше не будут выполняться итерации.

//will only run "do stuff" twice
for (int x = 0; x < 100; x++) {
  if (x == 2) {
    break;
  }
  //do stuff
}

continue завершит текущую итерацию и перейдет к следующей.

//will run "do stuff" until x >= 100 except for when x = 2
for (int x = 0; x < 100; x++) {
  if (x == 2) {
    continue;
  }
  //do stuff
}

Обратите внимание, что в цикле for «continue» оценивает выражение «part3» для «for (part1; part2; part3)»; Напротив, в цикле while он просто перескакивает, чтобы повторно оценить условие цикла.

160
ответ дан 24 November 2019 в 11:47
поделиться

Они практически одинаковы, за исключением цикла do-while. Цикл for хорош, когда у вас есть переменная типа counter. Это делает его очевидным. Цикл while имеет смысл в случаях, когда проверяется флаг, как показано ниже :

while (!done) {
   if (some condtion) 
      done = true;
}
2
ответ дан 24 November 2019 в 11:47
поделиться

Циклы For (по крайней мере, с учетом C99) превосходят циклы while, поскольку они ограничивают область действия увеличиваемой переменной (переменных).

Циклы Do while полезны, когда условие зависит от некоторых входных данных. Из трех типов петель они используются наиболее редко.

2
ответ дан 24 November 2019 в 11:47
поделиться

WHILE более гибкий. FOR является более кратким в тех случаях, когда он применяется.

FOR отлично подходит для циклов, у которых есть какой-то счетчик, например

for (int n=0; n<max; ++n)

Вы, конечно, можете выполнить то же самое с WHILE, как указывали другие, но теперь инициализация, проверка и приращение прерываются через три строки. Возможно три широко разделенных строки, если тело цикла большое. Из-за этого читателю сложнее увидеть, что вы делаете. В конце концов, хотя «++ n» - очень распространенная третья часть FOR, это, конечно, не единственная возможность. Я написал много циклов, в которых я пишу «n + = increment» или какое-нибудь более сложное выражение.

FOR, конечно же, может прекрасно работать с другими вещами, кроме счетчика. Как

for (int n=getFirstElementFromList(); listHasMoreElements(); n=getNextElementFromList())

И т. Д.

Но FOR перестает работать, когда логика «в следующий раз через цикл» становится более сложной. Учтите:

initializeList();
while (listHasMoreElements())
{
  n=getCurrentElement();
  int status=processElement(n);
  if (status>0)
  {
    skipElements(status);
    advanceElementPointer();
  }
  else
  {
    n=-status;
    findElement(n);
  }
}

То есть, если процесс продвижения может отличаться в зависимости от условий, встречающихся во время обработки, оператор FOR непрактичен. Да, иногда вы можете заставить его работать с достаточно сложными выражениями, использованием тернарного оператора?: И т.д., но это обычно делает код менее читаемым, а не более читаемым.

На практике большинство моих циклов либо проходят через массив, либо через какую-либо структуру, и в этом случае я использую цикл FOR; или читают файл или набор результатов из базы данных, и в этом случае я использую цикл WHILE («while (! eof ())» или что-то в этом роде).

2
ответ дан 24 November 2019 в 11:47
поделиться

Если есть серьезные опасения по поводу скорости и производительности, лучший подход - проверить код, созданный компилятором, на уровне сборки.

Например, следующий код показывает, что «do-while» немного быстрее. Это потому, что инструкция «jmp» не используется в цикле «do-while».

Кстати, в этом конкретном примере наихудший случай дается циклом for. :))

int main(int argc, char* argv[])
{
    int i;
    char x[100];

    // "FOR" LOOP:
    for (i=0; i<100; i++ )
    {
        x[i] = 0;
    }

    // "WHILE" LOOP:
    i = 0;
    while (i<100 )
    {
        x[i++] = 0;
    }

    // "DO-WHILE" LOOP:
    i = 0;
    do
    {
        x[i++] = 0;
    }
    while (i<100);

    return 0;
}

// ЦИКЛ "FOR":

    010013C8  mov         dword ptr [ebp-0Ch],0
    010013CF  jmp         wmain+3Ah (10013DAh)

  for (i=0; i<100; i++ )
  {
      x[i] = 0;
    010013D1  mov         eax,dword ptr [ebp-0Ch]  <<< UPDATE i
    010013D4  add         eax,1
    010013D7  mov         dword ptr [ebp-0Ch],eax
    010013DA  cmp         dword ptr [ebp-0Ch],64h  <<< TEST
    010013DE  jge         wmain+4Ah (10013EAh)     <<< COND JUMP
    010013E0  mov         eax,dword ptr [ebp-0Ch]  <<< DO THE JOB..
    010013E3  mov         byte ptr [ebp+eax-78h],0
    010013E8  jmp         wmain+31h (10013D1h)     <<< UNCOND JUMP
  }

// ЦИКЛ "WHILE":

  i = 0;
  010013EA  mov         dword ptr [ebp-0Ch],0
  while (i<100 )
  {
      x[i++] = 0;
    010013F1  cmp         dword ptr [ebp-0Ch],64h   <<< TEST
    010013F5  jge         wmain+6Ah (100140Ah)      <<< COND JUMP
    010013F7  mov         eax,dword ptr [ebp-0Ch]   <<< DO THE JOB..
    010013FA  mov         byte ptr [ebp+eax-78h],0
    010013FF  mov         ecx,dword ptr [ebp-0Ch]   <<< UPDATE i
    01001402  add         ecx,1
    01001405  mov         dword ptr [ebp-0Ch],ecx
    01001408  jmp         wmain+51h (10013F1h)      <<< UNCOND JUMP
  }

// ЦИКЛ "DO-WHILE":

i = 0;
.  0100140A  mov         dword ptr [ebp-0Ch],0
  do
  {
      x[i++] = 0;
    01001411  mov         eax,dword ptr [ebp-0Ch]   <<< DO THE JOB..
    01001414  mov         byte ptr [ebp+eax-78h],0
    01001419  mov         ecx,dword ptr [ebp-0Ch]   <<< UPDATE i
    0100141C  add         ecx,1
    0100141F  mov         dword ptr [ebp-0Ch],ecx
    01001422  cmp         dword ptr [ebp-0Ch],64h   <<< TEST
    01001426  jl          wmain+71h (1001411h)      <<< COND JUMP
  }
  while (i<100);
15
ответ дан 24 November 2019 в 11:47
поделиться

Одно из распространенных недоразумений с while / для циклов , которое я видел, заключается в том, что их эффективность различается. Циклы while и for одинаково эффективны . Я помню, как мой учитель по информатике из старшей школы сказал мне, что циклы for более эффективны для итераций, когда вам нужно увеличивать число. Это не относится к делу.

Циклы For просто синтаксически подслащены циклами while и ускоряют запись итерационного кода.

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

4
ответ дан 24 November 2019 в 11:47
поделиться
Другие вопросы по тегам:

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