Swift: Laços do Swift: for-in, while e repeat-while

Os laços permitem que um computador repita a mesma tarefa, como uma linha de montagem de fábrica funcionando sem parar. Esta lição aborda quando e como usar cada tipo de laço no Swift, com práticas recomendadas.

1. O Que Você Vai Aprender


2. Uma História Real de um Analista de Dados

(1) Problema: Processar manualmente 100 mil linhas de log — dedos quase caindo

Charlie é analista de dados em uma plataforma de e-commerce. Todo dia ele precisa examinar 100.000 linhas de log de servidor para contabilizar taxas de erro, tempos de resposta e padrões de anomalia. Ele começava copiando e colando manualmente linha por linha no Excel:

SWIFT
// The pain: manual line-by-line processing
let logEntry1 = "2026-07-15 10:23:45 [ERROR] DB timeout"
let logEntry2 = "2026-07-15 10:24:01 [INFO] Request completed"
// ... 99,998 more lines to go

Charlie passava 3 horas por dia nessa tarefa repetitiva e sempre deixava passar entradas. Ele precisava de uma ferramenta automatizada para iterar sobre todos os logs.

(2) A Solução com Laço for-in

SWIFT
let logEntries = [
    "2026-07-15 10:23:45 [ERROR] DB timeout",
    "2026-07-15 10:24:01 [INFO] Request completed",
    "2026-07-15 10:25:30 [ERROR] Connection refused"
]
var errorCount = 0
for entry in logEntries {
    if entry.contains("[ERROR]") {
        errorCount += 1
    }
}
print("Found \(errorCount) errors in log")

(3) Resultado: 3 horas reduzidas para 3 segundos

Métrica Excel Manual Automação com Laço
Tempo para 100 mil linhas 3 horas 3 segundos
Contagens perdidas/erradas 5-10 0
Reutilizável Não Sim (basta mudar o nome do arquivo)
Humor do Charlie Frustrado Feliz

3. Laços for-in

for-in é o laço mais usado no Swift. Ele itera sobre uma sequência — arrays, intervalos, dicionários e mais.

100%
graph LR
    A[Sequência] --> B[Próximo Elemento]
    B --> C[Executar Corpo]
    C --> D{Mais Elementos?}
    D -->|Sim| B
    D -->|Não| E[Continuar]
Percorrer Sintaxe Valor por Iteração
Array for item in array Elemento
Intervalo for i in 1...5 Valor do índice
Dicionário for (chave, val) in dict Tupla chave-valor
String for char in string Caractere
Array indexado for (i, item) in array.enumerated() Tupla (índice, elemento)

(1) Percorrendo Arrays e Intervalos

SWIFT
// Traverse an array
let fruits = ["apple", "banana", "orange"]
for fruit in fruits {
    print("I like \(fruit)")
}
// Traverse a range
for number in 1...5 {
    print("Count: \(number)")
}
// Indexed traversal
let colors = ["red", "green", "blue"]
for (index, color) in colors.enumerated() {
    print("\(index + 1). \(color)")
}

(2) Percorrendo Dicionários

SWIFT
let scores = ["Alice": 95, "Bob": 82, "Charlie": 78]
for (name, score) in scores {
    print("\(name): \(score)")
}

▶ Exemplo: Calculando a Temperatura Média Mensal

SWIFT
// ============================================
// Calculate average from temperature data using for-in
// ============================================
let monthlyTemps = [5.2, 8.1, 12.5, 18.3, 24.1, 30.2,
                    32.0, 31.5, 27.8, 21.3, 14.2, 8.9]
var total = 0.0
for temp in monthlyTemps {
    total += temp
}
let average = total / Double(monthlyTemps.count)
print("Total: \(total) C")
print("Average: \(String(format: "%.1f", average)) C")

Saída:

TEXT 📖 Somente leitura
Total: 234.1 C
Average: 19.5 C

4. while e repeat-while

while repete a execução enquanto uma condição for verdadeira — ótimo quando você não sabe o número exato de iterações. repeat-while garante pelo menos uma execução.

100%
graph TB
    subgraph "while"
        A[Verificar Condição] -->|true| B[Executar Corpo]
        B --> A
        A -->|false| C[Sair]
    end
    subgraph "repeat-while"
        D[Executar Corpo] --> E[Verificar Condição]
        E -->|true| D
        E -->|false| F[Sair]
    end
Tipo Momento da Verificação Execuções Mínimas Quando Usar
while Antes do corpo 0 Orientado por condição, pode nunca executar
repeat-while Depois do corpo 1 Garantido pelo menos uma vez, ex.: validação de entrada do usuário

(1) Laço while

SWIFT
var countdown = 5
while countdown > 0 {
    print("\(countdown)...")
    countdown -= 1
}
print("Liftoff!")

(2) Laço repeat-while

SWIFT
var attempts = 0
var success = false
repeat {
    attempts += 1
    print("Attempt #\(attempts)...")
    success = Int.random(in: 1...10) > 5
} while !success && attempts < 3
print(success ? "Succeeded!" : "Failed after 3 attempts")

▶ Exemplo: Jogo de Adivinhação de Números

SWIFT
// ============================================
// Number guessing game with repeat-while
// ============================================
import Foundation
let target = Int.random(in: 1...20)
var guess = 0
var attempts = 0
print("Guess a number between 1 and 20")
repeat {
    attempts += 1
    guess = Int.random(in: 1...20)
    print("Attempt \(attempts): guessed \(guess)")
    if guess < target {
        print("  Too low")
    } else if guess > target {
        print("  Too high")
    } else {
        print("  Correct!")
    }
} while guess != target
print("Solved in \(attempts) attempts!")

Saída:

TEXT 📖 Somente leitura
Guess a number between 1 and 20
Attempt 1: guessed 7
  Too low
Attempt 2: guessed 15
  Too high
Attempt 3: guessed 12
  Correct!
Solved in 3 attempts!

5. break, continue e Instruções Rotuladas

break sai imediatamente de um laço. continue pula a iteração atual e avança para a próxima. Instruções rotuladas permitem saltar para fora de múltiplos laços aninhados.

Instrução Efeito Caso de Uso
break Encerra o laço atual imediatamente Saída antecipada quando o alvo é encontrado
continue Pula a iteração atual, avança para a próxima Filtrar elementos indesejados
break <rotulo> Sai do laço rotulado nomeado Sair de laços aninhados
continue <rotulo> Pula para a próxima iteração do laço nomeado Controle de fluxo em laços aninhados

(1) break e continue

SWIFT
let numbers = [3, 7, 1, 9, 4, 6, 8]
// break: exit when first even number found
for num in numbers {
    if num.isMultiple(of: 2) {
        print("Found first even: \(num)")
        break
    }
}
// continue: only print odd numbers
for num in numbers {
    if num.isMultiple(of: 2) {
        continue
    }
    print("Odd: \(num)")
}

(2) Instruções Rotuladas

SWIFT
// Breaking out of multiple loops with a label
outerLoop: for i in 1...5 {
    for j in 1...5 {
        let product = i * j
        if product == 12 {
            print("Found: \(i) x \(j) = \(product)")
            break outerLoop
        }
    }
}

▶ Exemplo: Filtragem e Análise de Log

SWIFT
// ============================================
// Processing log data with break/continue
// ============================================
let logEntries = [
    "INFO Server started",
    "ERROR Database connection failed",
    "DEBUG Cache hit ratio 85%",
    "ERROR Timeout after 30s",
    "INFO Request completed in 120ms",
    "ERROR Disk space low"
]
var errorCount = 0
for entry in logEntries {
    if entry.hasPrefix("DEBUG") {
        continue
    }
    if entry.hasPrefix("ERROR") {
        errorCount += 1
        print("[ERROR #\(errorCount)] \(entry)")
    }
    if errorCount >= 5 {
        print("ALERT: Too many errors!")
        break
    }
}
print("Processed \(logEntries.count) entries, found \(errorCount) errors")

Saída:

TEXT 📖 Somente leitura
[ERROR #1] ERROR Database connection failed
[ERROR #2] ERROR Timeout after 30s
[ERROR #3] ERROR Disk space low
Processed 6 entries, found 3 errors

6. Exemplo Completo: Ferramenta de Análise de Log em Lote

SWIFT
// ============================================
// Log analysis tool
// Combining for-in / while / break / continue
// ============================================
import Foundation
let logs = [
    "[INFO] 2026-07-15 08:00:00 Server started",
    "[ERROR] 2026-07-15 08:05:23 DB connection timeout",
    "[INFO] 2026-07-15 08:10:45 Cache warmed up",
    "[ERROR] 2026-07-15 08:15:30 Disk I/O error",
    "[WARN] 2026-07-15 08:20:00 Memory usage 85%",
    "[ERROR] 2026-07-15 08:25:10 Request failed: timeout",
    "[INFO] 2026-07-15 08:30:00 Health check OK",
    "[DEBUG] 2026-07-15 08:35:00 Query plan: index scan",
    "[ERROR] 2026-07-15 08:40:00 Connection pool exhausted"
]
var stats = (info: 0, warn: 0, error: 0, debug: 0)
var errorLines: [String] = []
for entry in logs {
    if entry.hasPrefix("[DEBUG]") {
        stats.debug += 1
        continue
    }
    if entry.hasPrefix("[ERROR]") {
        stats.error += 1
        errorLines.append(entry)
    } else if entry.hasPrefix("[WARN]") {
        stats.warn += 1
    } else if entry.hasPrefix("[INFO]") {
        stats.info += 1
    }
}
print("=== Log Analysis Report ===")
print("Total entries: \(logs.count)")
print("INFO: \(stats.info) | WARN: \(stats.warn) | ERROR: \(stats.error) | DEBUG: \(stats.debug)")
if stats.error > 0 {
    print("\n=== Error Details ===")
    var i = 0
    while i < errorLines.count {
        print("\(i + 1). \(errorLines[i])")
        i += 1
    }
    print("\nError rate: \(Double(stats.error) / Double(logs.count) * 100)%")
}

Saída:

TEXT 📖 Somente leitura
=== Relatório de Análise de Log ===
Total de entradas: 9
INFO: 3 | AVISO: 1 | ERRO: 4 | DEBUG: 1

=== Detalhes dos Erros ===
1. [ERRO] 2026-07-15 08:05:23 Timeout na conexão BD
2. [ERRO] 2026-07-15 08:15:30 Erro de E/S no disco
3. [ERRO] 2026-07-15 08:25:10 Requisição falhou: timeout
4. [ERRO] 2026-07-15 08:40:00 Pool de conexões esgotado

Taxa de erro: 44.4%

❓ Perguntas Frequentes

P: Como escolher entre for-in e while? R: Use for-in quando souber o que está iterando (arrays, intervalos etc.). Use while quando o número de iterações for desconhecido e orientado por condição. Use repeat-while quando precisar de pelo menos uma execução. P: O índice de enumerated() começa em 0 ou 1? R: Começa em 0. Se quiser exibir a partir de 1, basta adicionar 1 ao imprimir. P: Qual é a diferença real entre while e repeat-while? R: while verifica a condição antes de executar o corpo — pode executar zero vezes. repeat-while executa o corpo primeiro e depois verifica — garantido pelo menos uma execução. P: Qual é a diferença entre break e continue? R: break encerra todo o laço. continue pula a iteração atual e avança para a próxima. Analogia: break é sair do cinema; continue é pular uma cena chata, mas ficar para assistir o resto. P: Há restrições quanto aos nomes dos rótulos? R: Nomes de rótulos são identificadores personalizados. Convencionalmente, use nomes significativos como lacoExterno ou lacoLinha, seguidos por dois pontos, colocados antes do for ou while.


📖 Resumo


📝 Exercícios

  1. Iniciante: Use for-in para iterar de 1 a 10 e imprimir o quadrado de cada número (ex.: "O quadrado de 2 é 4").
  2. Intermediário: Use while para implementar um contador simples: comece de 100 e subtraia 7 a cada vez, imprimindo o valor de cada etapa até que o número seja menor que 0.
  3. Desafio: Escreva um programa de laço aninhado que gere uma tabuada 9x9. Use instruções rotuladas e break/continue para controlar a formatação da saída (ex.: pular linhas de múltiplos de 5).
Web-Tutorial.com

Equipe Técnica Web-Tutorial

Uma plataforma de tutoriais mantida por diversos desenvolvedores. Cada tutorial é escrito e revisado por profissionais da área correspondente. Trabalhamos para manter nosso conteúdo preciso e confiável — se encontrar algum problema, avise-nos.

100%