In our last article we covered for loops โ perfect for when you know exactly how many times you need to repeat something. But what happens when you don't know how many times you'll need to loop?
That's where while and repeat loops come in. ๐ง
๐ The While Loop โ Run Until a Condition Is False
A while loop keeps running as long as a condition is true. The moment the condition becomes false, the loop stops:
while someCondition {
// code to repeat
}
No array needed. No range needed. Just a condition. Let's see it in action:
var countdown = 10
while countdown > 0 {
print("\(countdown)...")
countdown -= 1
}
print("Blast off! ๐")
Output:
10...
9...
8...
7...
6...
5...
4...
3...
2...
1...
Blast off! ๐
Breaking it down:
- We start with
countdown = 10 - The loop checks
countdown > 0before every iteration - Inside the loop we print the number and subtract 1
- When
countdownhits 0 the condition becomes false and the loop stops - The final message prints after the loop ends
๐ฒ Random Numbers + While Loops โ A Perfect Combo
Here's where while loops really shine โ when you genuinely don't know how many times you'll need to loop.
Swift gives us a fantastic tool called random(in:) that generates a random number within a range:
let id = Int.random(in: 1...1000) // random Int between 1 and 1000
let amount = Double.random(in: 0...1) // random Double between 0 and 1
Now let's combine this with a while loop. Imagine you're playing a game and need to keep rolling a dice until you land a critical hit โ a 20 on a 20-sided dice:
var roll = 0
while roll != 20 {
roll = Int.random(in: 1...20)
print("Rolled: \(roll)")
}
print("Critical hit! โ๏ธ")
Output (will vary every time):
Rolled: 7
Rolled: 13
Rolled: 4
Rolled: 19
Rolled: 20
Critical hit! โ๏ธ
Every time you run this code you'll get a different result โ sometimes lucky, sometimes not. This is impossible to replicate cleanly with a for loop because you simply don't know how many rolls it will take. That's the whole point of while. ๐ฏ
๐ฎ Another Example โ Grinding for Power
Let's say you're building an RPG and a character needs to keep training until their power level hits 9000:
var powerLevel = 1
var trainingRounds = 0
while powerLevel < 9000 {
let gainedPower = Int.random(in: 100...500)
powerLevel += gainedPower
trainingRounds += 1
print("Round \(trainingRounds): Power level \(powerLevel)")
}
print("Power level is over 9000! ๐ฅ Took \(trainingRounds) rounds.")
Output (varies every run):
Round 1: Power level 342
Round 2: Power level 719
Round 3: Power level 1205
...
Power level is over 9000! ๐ฅ Took 21 rounds.
We have no idea how many rounds it will take โ that's determined at runtime by the random numbers. A for loop just can't handle this kind of uncertainty. A while loop handles it perfectly. โ
โ ๏ธ Watch Out โ Infinite Loops
One thing to be careful about with while loops โ if your condition never becomes false, the loop runs forever and your app freezes. This is called an infinite loop:
// โ ๏ธ DON'T DO THIS
while true {
print("This never stops!")
}
Always make sure something inside your loop will eventually make the condition false โ like decrementing a counter or checking a value that will change. ๐
๐ The Repeat Loop โ Always Run At Least Once
Swift has one more loop type that doesn't get talked about as much โ the repeat loop. It's similar to while with one key difference:
A
whileloop checks its condition before running.
Arepeatloop checks its condition after running โ meaning it always runs at least once.
Here's the structure:
repeat {
// code to run
} while condition
๐ค Why Does This Matter?
Let's say you want to shuffle an array of numbers and make sure the result is different from the original. With a regular while loop you'd write:
let numbers = [1, 2, 3, 4, 5]
var random = numbers.shuffled() // shuffle once here
while random == numbers {
random = numbers.shuffled() // and again here if needed ๐ฌ
}
Notice the problem โ numbers.shuffled() appears twice. That's unnecessary repetition. If that shuffle logic was more complex โ say 10 or 20 lines โ you'd be maintaining the same code in two places.
This is where the programming principle DRY comes in โ Don't Repeat Yourself. Write code once, not twice. ๐ซ
โ The Cleaner Way โ repeat
Here's the same logic using repeat:
let numbers = [1, 2, 3, 4, 5]
var random: [Int]
repeat {
random = numbers.shuffled()
} while random == numbers
print(random)
Much cleaner! The shuffle happens inside the loop body once, then the condition is checked. If the shuffled result matches the original, it shuffles again. If not, it stops. The shuffling code only exists once โ no repetition, no maintenance headache. ๐ธ
๐ฎ Another Example โ Generating a Unique Battle Code
let usedCodes = [1234, 5678, 9012]
var battleCode: Int
repeat {
battleCode = Int.random(in: 1000...9999)
} while usedCodes.contains(battleCode)
print("Your unique battle code: \(battleCode) โ๏ธ")
The code runs at least once, generates a random number, then checks if it's already been used. If it has, it generates another. This guarantees we always get a fresh code โ and the generation logic only lives in one place.
๐ For vs While vs Repeat โ Which to Use?
| Situation | Best choice |
|---|---|
| Looping over an array or set |
for loop |
| Looping a fixed number of times |
for loop |
| Looping until a condition is met |
while loop |
| Don't know how many iterations needed |
while loop |
| Need to run at least once, then check |
repeat loop |
| Avoiding duplicate code before a loop |
repeat loop |
A simple way to think about it:
- For loops โ you know the finish line before you start ๐
- While loops โ you run until something tells you to stop ๐
- Repeat loops โ you run first, then decide whether to stop ๐
๐งฉ Putting It All Together
Here's a mini battle system using all three concepts:
var health = 100
var bossHealth = 150
var round = 1
print("โ๏ธ Battle Start!")
print()
// While loop โ keep fighting until someone loses
while health > 0 && bossHealth > 0 {
let playerDamage = Int.random(in: 10...30)
let bossDamage = Int.random(in: 5...20)
bossHealth -= playerDamage
health -= bossDamage
print("Round \(round):")
print(" You dealt \(playerDamage) โ Boss health: \(max(0, bossHealth))")
print(" Boss dealt \(bossDamage) โ Your health: \(max(0, health))")
print()
round += 1
}
if health > 0 {
print("๐ You won in \(round - 1) rounds!")
} else {
print("๐ Defeated in \(round - 1) rounds. Try again!")
}
// Repeat loop โ generate a unique reward code
let usedCodes = [1111, 2222, 3333]
var rewardCode: Int
repeat {
rewardCode = Int.random(in: 1000...9999)
} while usedCodes.contains(rewardCode)
print("๐ Your reward code: \(rewardCode)")
๐ Wrap Up
Now you know all three loop types in Swift:
-
forโ when you know exactly how many times to loop -
whileโ when you loop until a condition becomes false, checked before each run -
repeatโ when you always need at least one run, condition checked after
And remember โ always make sure your while or repeat condition will eventually become false, or you'll end up with an infinite loop! ๐
Next up we'll look at how to skip loop iterations and exit loops early using continue and break. See you there! ๐
Top comments (4)
WOW! Awesome โค๏ธ
Thank you so much! ๐ธ Really glad you enjoyed it โ more articles coming soon, hope you find those helpful too! ๐โจ
Welcome! I also hope that you'll upload the post soon ๏ฝกโ โโ โฟโ โโ ๏ฝก
Haha, yes, absolutely. The next one is already on its wayโstay tuned! ๐ธ๐๐