Doing It Again

Every program so far has run each statement at most once. Loops remove that ceiling, and with them C is complete: sequence, selection, repetition, everything else in the language is convenience. This lesson covers the two condition-driven loops, while and do-while, the difference between checking before and checking after, and the loop shapes that power real input processing.

while: Check, Then Run

while (condition) {
    /* body: runs while condition stays non-zero */
}

The condition is tested before every pass, the body runs if it is non-zero, and the loop ends the first time the test fails. If the condition is false on arrival, the body runs zero times, which is a feature: "process every item" correctly does nothing when there are no items.

The discipline that keeps while honest is remembering that something in the body must move the condition toward false. A counter the body increments, input the body consumes, a total the body grows past a limit. Forget it and the loop runs forever; the classic instance is an update line accidentally deleted or placed outside the braces.

Sentinel Loops: The Real Workhorse

Counting is the textbook example; reading until a marker is the real job. A sentinel loop consumes input until a special value says stop, and it composes beautifully with the guarded scanf from chapter 5:

Enter numbers separated by spaces or newlines, ending with 0. Read the condition carefully, because it is chapter 3 and 4 paying off at once: scanf must succeed (== 1), and then the value must not be the sentinel; &&'s short-circuit guarantees the sentinel test only looks at a value that was actually read. Bad input ends the loop too, since scanf stops returning 1: this loop cannot run forever on garbage.

The chapter 4 preview is now fully yours as well: while ((ch = getchar()) != EOF) is a sentinel loop whose sentinel is end-of-input itself, with the parentheses that precedence demands.

do-while: Run, Then Check

do {
    /* body: always runs at least once */
} while (condition);

do-while tests after the body, so the body executes at least once regardless. Note the semicolon after the closing parenthesis, a favorite spot-the-error exam detail. The textbook name for the distinction: while is entry-controlled, do-while is exit-controlled.

Use it when "at least once" is a fact of the problem, and the honest examples are menus and retry prompts: show the menu, read the choice, repeat while the choice is invalid. The act must happen before there is anything to test. In practice while fits most problems, and if you find yourself contorting logic so the body runs first, the problem is usually telling you it wants while.

Counting digits is the canonical honest do-while: even the number 0 has one digit, so the body must run at least once, and chapter 3's / 10 digit-peeling does the work. Try 0, 7, and 10000.

The Infinite Loop, Named

while (1) runs forever on purpose, real programs use it for "serve requests until killed", paired with break, next lesson's tool, to exit from the middle. The accidental version has a long exam pedigree: while (i = 10) assigns instead of compares and never ends; a body that never touches the condition's variables never ends; and the chapter 4 warning about a char holding getchar's result never matching EOF is an infinite loop in disguise on this very platform.

Key Takeaways

  • while tests before each pass and may run zero times; something in the body must push the condition toward false.
  • The sentinel shape while (scanf("%d", &v) == 1 && v != stop) reads until a marker, ends safely on bad input, and is the pattern behind real input processing.
  • while ((ch = getchar()) != EOF) is the same shape with end-of-input as the sentinel.
  • do-while tests after the body, runs at least once, ends with a semicolon, and fits menus, retries, and digit counting.
  • while (1) is the deliberate infinite loop; = for == and untouched condition variables are the accidental ones.