For
-loopIn Swift 5.8 programs we use a for-in
loop to iterate forward. We repeat statements. We access indexes and elements with enumerated
. While is also used.
To loop over the characters in a string
, we must use indexes. We start at startIndex
and stop when endIndex
is reached. We cannot just access chars with Ints.
for-in
This loop is a "for-each
" loop. It acts upon a range or a collection like an array. Here we use a range of the numbers 0, 1, 2 and 3.
// Use a for-loop over the range. // ... The range is inclusive so all numbers are included. for i in 0...3 { print(i) } // An underscore can be used in place of an identifier name. for _ in 0...3 { print("Hello") }0 1 2 3 Hello Hello Hello Hello
In Swift 4 the for-in
loop is emphasized. Here we see the exclusive bound syntax, where we continue to one minus the maximum.
// Use exclusive maximum in for-loop. for i in 0..<3 { print("EXCLUSIVE LOOP:", i) }EXCLUSIVE LOOP: 0 EXCLUSIVE LOOP: 1 EXCLUSIVE LOOP: 2
The for
-loop gets most of the attention in programs. But "while" is also useful. It continues iterating while a condition evaluates to true.
while
-loop. The loop stops when "i" is -1.var i = 5 // Decrement i while it is greater than or equal to 0. while i >= 0 { print(i) i -= 1 }5 4 3 2 1 0
This program uses the break
keyword in a while
-loop to stop the loop. It tests for even numbers, and after 3 even numbers have been encountered, it breaks.
while-true
loop. We can use while "true" to continue a loop infinitely until a break
(or return) is reached.var i = 5 var evenCount = 0 // Break loop when the third even number is encountered. while true { if i % 2 == 0 { print("Even") evenCount += 1 if evenCount == 3 { break } } print(i) i += 1 }5 Even 6 7 Even 8 9 Even
In a loop, the continue statement stops the current iteration, but does not terminate the entire loop. The next iteration is started.
// Loop over the numbers 0 through 10. for i in 0...10 { // If number is even, continue to the next iteration. if (i % 2) == 0 { continue } // Print remaining numbers. print(i) }1 3 5 7 9
String
charactersIt is possible to loop over the characters in a String
in Swift with a for
-loop. We can directly access each Character this way.
let values = "abc" // Loop over Characters in String. for c in values { print(c) }a b c
The enumerated()
func
can be used with a for
-loop. A tuple of the index and value is returned for use in each iteration of the loop. Here we enumerate a String
array.
let codes = ["XX", "XY", "YZ"] // Loop over each index and value in the array. for (index, value) in codes.enumerated() { print("\(index) \(value)") }0 XX 1 XY 2 YZ
For more complex algorithms, we can nest loops. In the inner block, we can access both the outer and the inner iteration variables.
// A for-loop can be nested. for i in 0...2 { for y in 0...2 { // Access both iteration variables in inner block. print("\(i), \(y)") } }0, 0 0, 1 0, 2 1, 0 1, 1 1, 2 2, 0 2, 1 2, 2
This loop continues iterating over a block while the condition (specified after the block) is true. It is the same as a do-while
loop in other languages like C.
var size = 10 repeat { // Increment. size += 1 // Print the value. print(size) } while size < 1611 12 13 14 15 16
A range must go from low (the start index) to high (the end index). The short
syntax does not support a decrementing range.
// This will not work: a range must go from low to high. for i in 10...3 { print(i) }fatal error: Can't form Range with end < start (lldb)
Here is a loop that accesses adjacent elements based on indexes. It uses enumerated()
and ensures each index is the start of a pair.
for
-enumerated()
loop is powerful. It can accommodate many requirements (like adjacent accesses).let positions = [10, 20, 30, 40, 50, 60] // Loop over elements and indexes in array. for (index, element) in positions.enumerated() { // See if index is even and not the last index. if index % 2 == 0 && index + 1 < positions.count { // Get adjacent elements. let next = positions[index + 1] print("\(element), \(next)") } }10, 20 30, 40 50, 60
In Swift 3 the C-style for
-statement was removed. We must use enumerated()
to iterate over the indexes and elements. A while
-loop can also be a substitute.
// This does not work in Swift 3. for var i = 0; i < 4; i++ { print(i) }main.swift:2:1: C-style for statement has been removed in Swift 3 main.swift:2:24: '++' is unavailable: it has been removed in Swift 3
Loops are important in most programs. And most of the time spent in programs is spent in loops. This is a good focus for optimization efforts.