How does do-while work in EK9?
← Control Flow · Ref: Q67
EK9's do-while loop executes the body first, then checks the condition. This guarantees the body runs at least once, unlike a regular while loop that may not execute at all.
BASIC DO-WHILE
The body executes before the condition is checked:
counter <- 0 do stdout.println($counter) counter: counter + 1 while counter < 5
This prints 0, 1, 2, 3, 4. The body executes first, then 'counter < 5' is checked.
AT-LEAST-ONCE GUARANTEE
Even if the condition is false from the start, the body still runs once:
threshold <- 100 do stdout.println("Runs once") while threshold < 10
The body prints 'Runs once' even though 100 is not less than 10.
WHEN TO USE DO-WHILE
Use do-while when you need at least one execution before checking the condition:
- Reading user input (try once, then check if valid)
- Processing a batch (do one iteration, check if more)
- Retry logic (attempt once, check if succeeded)
DO-WHILE VS WHILE
while: Checks BEFORE each iteration. Body may never execute.
do-while: Checks AFTER each iteration. Body always runs at least once.
// while: might not run while hasData() process()
// do-while: always runs once do process() while hasMoreData()
NO BREAK
Like all loops in EK9, do-while has no break statement. Structure your condition to control when the loop ends. See Q144 for why break was removed.
Do-while supports guard variables (see Q74) and can return values as an expression (see Q81).
See Q66 for while loops. See Q64 for for-range loops. See Q65 for for-in loops. See Q89 for stream pipelines as loop alternatives. See Q125 for head as the only early exit mechanism.
Example
defines module qa.flow.postcondition.loop defines function supplyStart() as pure -> initial as Integer <- rtn as Integer: initial defines program DoWhileDemo() stdout <- Stdout() // === BASIC DO-WHILE === counter <- supplyStart(0) loopLimit <- 5 do stdout.println(`Counter: ${counter}`) counter: counter + 1 while counter < loopLimit // === AT-LEAST-ONCE GUARANTEE === // Even though 100 > 10, body runs once threshold <- supplyStart(100) ran <- false maxCount <- 10 do ran: true while threshold < maxCount stdout.println(`Ran at least once: ${ran}`) // === ACCUMULATION === sum <- 0 n <- supplyStart(1) maxIterations <- 10 do sum: sum + n n: n + 1 while n <= maxIterations stdout.println(`Sum 1..10: ${sum}`) // === BUILDING A STRING === built <- String() i <- supplyStart(1) countdown <- 5 do if length built > 0 built: built + ", " built: built + $i i: i + 1 while i <= countdown stdout.println(`Built: ${built}`)
Common mistakes
E07390 — EK9 has no break statement. Place the real termination condition in the while clause rather than using break inside the body. See ek9 -h E07390 for details.
Incorrect:
do stdout.println(`Counter: ${counter}`) counter: counter + 1 if counter >= loopLimit break while true
Correct:
do stdout.println(`Counter: ${counter}`) counter: counter + 1 while counter < loopLimit
Other ways to ask this
- How do I write a loop that runs at least once in EK9?
- What is the do-while syntax in EK9?
- How do I loop with the condition at the end in EK9?
Coming from another language?
Java: do { } while (condition); with braces, parentheses, and semicolon required. C/C++: do { } while (condition); same syntax as Java. Python: no do-while construct, use while True with break instead. Rust: no do-while, use loop { if !condition { break } } instead. Go: no do-while, use for { if !condition { break } } instead. Kotlin: do { } while (condition) similar to Java but no semicolon. C#: do { } while (condition); same as Java. JavaScript: do { } while (condition); same as Java. Swift: repeat { } while condition with 'repeat' keyword instead of 'do'. EK9: do ... while condition with indentation, no braces, no parentheses, no semicolon, no break available, guard variables supported.
Keywords: atleast, once, condition, while, flow, first, post, control, body, repeat, loop, branch, do