Chapter 55: Swift Repeat/While Loop
1. The most important difference between while and repeat … while
| Loop type | When is the condition checked? | Minimum number of executions | Typical English translation | Most common real-life feeling |
|---|---|---|---|---|
| while condition { … } | Before the body | 0 times (might never run) | “While this is true, do the body” | “Only do it if the condition is already true” |
| repeat { … } while condition | After the body | At least 1 time | “Do the body at least once, then keep doing it while condition is true” | “Do it once, then check if we should continue” |
The golden sentence you should remember forever:
repeat … while = “do it at least once, then keep going only if needed”
2. Very first examples – feel the difference
Example 1 – Simple counter (shows minimum 1 execution)
|
0 1 2 3 4 5 6 7 8 9 10 11 |
var count = 1 repeat { print("Count is now: \(count)") count += 1 } while count <= 3 |
Output (always runs at least once):
|
0 1 2 3 4 5 6 7 8 |
Count is now: 1 Count is now: 2 Count is now: 3 |
Now change the condition so it would be false from the beginning:
|
0 1 2 3 4 5 6 7 8 9 10 11 |
var count = 10 repeat { print("This line will still run once! Count = \(count)") count += 1 } while count <= 5 |
Output:
|
0 1 2 3 4 5 6 |
This line will still run once! Count = 10 |
→ Even though the condition is already false, the body ran once.
Compare with normal while:
|
0 1 2 3 4 5 6 7 8 9 10 |
var count = 10 while count <= 5 { print("This will never print") } |
→ Nothing is printed — loop body never executes.
3. Real-life examples — situations where repeat … while feels natural
Example 1 – Ask user for input until valid (most classic use case)
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
var pin: String? repeat { print("Enter a 4-digit PIN:") pin = readLine() if let pin = pin { if pin.count != 4 || !pin.allSatisfy({ $0.isNumber }) { print("PIN must be exactly 4 digits (0-9). Try again.") } } else { print("Please type something.") } } while pin == nil || pin!.count != 4 || !pin!.allSatisfy({ $0.isNumber }) print("PIN accepted: \(pin!)") |
Why repeat … while is perfect here:
- You must ask at least once — you cannot skip asking just because the user hasn’t entered anything yet
- You keep asking only if the input is invalid
Example 2 – Game loop: “Play again?” (very common in small games / tools)
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
var playAgain = "yes" repeat { print("Playing a round of the game… 🎲") // pretend game happens here print("Play another round? (yes/no)") if let input = readLine()?.lowercased() { playAgain = input } else { playAgain = "no" } } while playAgain == "yes" || playAgain == "y" print("Thanks for playing! Goodbye 👋") |
Example 3 – Keep trying until success (retry pattern)
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
var success = false var attempts = 0 let maxAttempts = 5 repeat { attempts += 1 print("Attempt \(attempts)/\(maxAttempts)…") // pretend network call or risky operation success = Bool.random() // 50% chance if !success { print("Failed. Waiting 1 second before retry...") Thread.sleep(forTimeInterval: 1.0) } } while !success && attempts < maxAttempts if success { print("Success after \(attempts) attempts!") } else { print("Failed after \(maxAttempts) attempts. Giving up.") } |
Typical retry pattern with repeat … while:
- Try at least once
- Keep trying while failed and attempts not exceeded
4. Very Common Beginner Mistakes & How to Avoid Them
| Mistake | Wrong / Dangerous code | Correct / Better habit | Why? |
|---|---|---|---|
| Forgetting to update the loop variable | repeat { print(“hi”) } while true | Make sure something changes the condition | Infinite loop |
| Using repeat … while when while is enough | repeat { … } while count < 10 (count starts ok) | Use normal while if 0 executions are possible | repeat forces at least one run |
| Force-unwrapping inside loop | repeat { let x = optional! } while … | guard let x = optional else { break } | Avoids crash when nil |
| No clear exit condition | repeat { … } while true without break | Always have a safe exit (counter, flag, etc.) | Infinite loop risk |
| Using repeat when for or forEach is clearer | var i=0; repeat { … i+=1 } while i<10 | for i in 0..<10 { … } | for is usually safer & clearer |
5. Quick Reference – When to choose repeat … while
| Situation | Prefer repeat … while? | Prefer normal while? | Prefer for-in? | Reason / guideline |
|---|---|---|---|---|
| Must run at least once | Yes | — | — | Asking for input, do-while logic |
| Retry until success (network, user input…) | Yes | Sometimes | — | Guarantees first try |
| You know the number of iterations | — | — | Yes | for i in 0..<count is clearer & safer |
| Loop until a collection becomes empty | Yes | Yes | — | while !array.isEmpty { … } |
| Waiting for external condition (user, sensor…) | Yes | Yes | — | Classic do-while situation |
6. Small Practice – Try these right now
- Countdown with guarantee Start with count = 0 Use repeat … while to print from 1 to 5 (show that it runs even if you change the condition to false from start)
- PIN validator Keep asking for a 4-digit PIN until the user enters exactly 4 digits (0-9 only)
- Retry pattern Simulate a task that succeeds with 30% chance Try up to 5 times Print attempt number each time Stop early on success
Paste your code here if you want feedback, corrections, or more elegant versions!
What would you like to explore next?
- while let pattern (very common with optionals)
- Infinite loops — how to debug & prevent them safely
- while vs repeat … while vs for — decision guide
- Loops in SwiftUI (ForEach vs manual while)
- Or move to another topic (switch, functions, arrays, optionals…)
Just tell me — we’ll continue in the same clear, patient, detailed style 😊
