Dessugar de for
map e flatMap.
Dessugar de for é uma aula grátis de Scala for Backend Engineering & Functional Programming no CoddyKit. Esta é a aula 1 de 4. Você pode ler a aula completa abaixo gratuitamente — depois pratica ao vivo no navegador com um editor de código integrado e um tutor de IA 24/7. Faz parte do caminho de aprendizado de Scala for Backend Engineering & Functional Programming, e seu progresso é sincronizado entre a web e o app CoddyKit. O curso de Scala for Backend Engineering & Functional Programming inclui 4 aulas no total.
O que é uma compreensão for?
Uma compreensão for no Scala é uma sintaxe especial para trabalhar com coleções e outros tipos de contêiner. Ela se parece com um laço imperativo, mas na verdade é um recurso sintático que o compilador reescreve em chamadas de map, flatMap, filter e foreach.
Entender essa simplificação ajuda você a raciocinar sobre qualquer compreensão for, inclusive sobre tipos personalizados.
object Main {
def main(args: Array[String]): Unit = {
val result = for (x <- List(1, 2, 3)) yield x * 10
println(result)
}
}Um único gerador se torna map
Quando uma compreensão for tem exatamente um gerador e usa yield, o compilador a reescreve em uma única chamada de map.
for (x <- xs) yield f(x)- torna-se
xs.map(x => f(x))
object Main {
def main(args: Array[String]): Unit = {
val a = for (x <- List(1, 2, 3)) yield x + 1
val b = List(1, 2, 3).map(x => x + 1)
println(a == b)
}
}A palavra-chave yield
A palavra-chave yield informa ao Scala que deve coletar os resultados em uma nova coleção do mesmo tipo.
Sem yield, a compreensão for executa um efeito colateral para cada elemento e retorna Unit (ela se torna foreach).
object Main {
def main(args: Array[String]): Unit = {
// No yield: side effect only
for (x <- List("a", "b")) println(x)
// With yield: builds a new List
val upper = for (x <- List("a", "b")) yield x.toUpperCase
println(upper)
}
}Dois geradores se tornam flatMap + map
Com dois ou mais geradores, os geradores externos se tornam flatMap e o mais interno se torna map.
for (x <- xs; y <- ys) yield f(x, y)- torna-se
xs.flatMap(x => ys.map(y => f(x, y)))
object Main {
def main(args: Array[String]): Unit = {
val pairs = for {
x <- List(1, 2)
y <- List("a", "b")
} yield (x, y)
println(pairs)
}
}Vendo o flatMap equivalente
Aqui, escrevemos a mesma lógica das duas formas. Provar que são iguais demonstra que as compreensões for não adicionam mágica, apenas legibilidade.
object Main {
def main(args: Array[String]): Unit = {
val sugar = for {
x <- List(1, 2)
y <- List(10, 20)
} yield x + y
val desugared = List(1, 2).flatMap(x => List(10, 20).map(y => x + y))
println(sugar)
println(sugar == desugared)
}
}Por que flatMap para o gerador externo
Cada elemento externo produz uma coleção inteira de resultados internos. Se usássemos map para o gerador externo, obteríamos uma coleção aninhada, como List(List(...), List(...)).
flatMap achata essas listas aninhadas em um único resultado plano.
object Main {
def main(args: Array[String]): Unit = {
val nested = List(1, 2).map(x => List(10, 20).map(y => x + y))
val flat = List(1, 2).flatMap(x => List(10, 20).map(y => x + y))
println(nested)
println(flat)
}
}for sem yield é foreach
Um laço for sem yield é reescrito em foreach. Ele executa o corpo pelos efeitos colaterais e produz Unit.
for (x <- xs) doSomething(x)- torna-se
xs.foreach(x => doSomething(x))
object Main {
def main(args: Array[String]): Unit = {
val r: Unit = for (x <- List(1, 2, 3)) print(x + " ")
println()
println("Return type is Unit")
}
}O tipo do resultado segue o primeiro gerador
O tipo do resultado é determinado pela coleção do primeiro gerador. Um for sobre uma List produz uma List; sobre um Set, um Set; sobre uma Option, uma Option.
object Main {
def main(args: Array[String]): Unit = {
val fromList = for (x <- List(1, 2, 2, 3)) yield x
val fromSet = for (x <- Set(1, 2, 2, 3)) yield x
println(fromList)
println(fromSet)
}
}Vinculando valores com =
Dentro de uma compreensão for, você pode vincular valores intermediários com =. Isso evita recomputações e melhora a legibilidade.
Ela é simplificada para um map que transporta o valor adicional em uma tupla.
object Main {
def main(args: Array[String]): Unit = {
val result = for {
x <- List(1, 2, 3)
doubled = x * 2
} yield doubled + 1
println(result)
}
}Funciona com qualquer tipo que tenha map/flatMap
Como a simplificação depende apenas de map e flatMap, as compreensões for funcionam com qualquer tipo que defina esses métodos: Option, Either, Try, Future e suas próprias classes.
object Main {
def main(args: Array[String]): Unit = {
val combined = for {
a <- Some(2)
b <- Some(3)
} yield a * b
println(combined)
}
}A verdadeira vantagem é a legibilidade
Compare uma cadeia profundamente aninhada de flatMap/map com uma compreensão for clara. Elas são compiladas para a mesma coisa, mas a versão com for é lida de cima para baixo como uma receita.
object Main {
def main(args: Array[String]): Unit = {
val chained = List(1, 2).flatMap(a => List(3, 4).map(b => a * b))
val readable = for {
a <- List(1, 2)
b <- List(3, 4)
} yield a * b
println(chained == readable)
}
}Verificação rápida
Como o compilador simplifica uma compreensão for com dois geradores e um yield?
Recapitulação
Você aprendeu como as compreensões for são simplificadas:
- Um gerador +
yield→map - Vários geradores +
yield→flatMap(externo) +map(interno) - Sem
yield→foreachretornandoUnit - Vinculações
val =adicionam valores intermediários - O tipo do resultado segue o primeiro gerador
Qualquer tipo com map e flatMap pode ser usado em uma compreensão for.
Perguntas Frequentes
A aula “Dessugar de for” é grátis?
Sim — o texto completo de “Dessugar de for” é grátis para ler aqui na web. Para praticá-la interativamente (um editor de código integrado e um tutor de IA 24/7) e desbloquear o restante do curso de Scala for Backend Engineering & Functional Programming, atualize para CoddyKit PRO. O curso de Scala for Backend Engineering & Functional Programming inclui 4 aulas no total.
O que vou aprender em “Dessugar de for”?
map e flatMap. Você pratica Scala for Backend Engineering & Functional Programming com código prático que executa diretamente no navegador, e um tutor de IA 24/7 responde suas dúvidas enquanto trabalha na aula.
Preciso ter experiência prévia para começar Scala for Backend Engineering & Functional Programming?
Nenhuma experiência prévia é necessária. Scala for Backend Engineering & Functional Programming no CoddyKit é estruturado para alunos iniciantes até avançados, então você pode começar aqui ou desde o início e aprender no seu ritmo. Esta é a aula 1 de 4.
Quanto tempo leva a aula “Dessugar de for”?
A maioria das aulas CoddyKit leva cerca de 5–10 minutos. Cada uma é compacta e interativa, então você faz progresso constante e retoma exatamente de onde parou entre web e app.
Posso escrever e executar código nesta aula de Scala for Backend Engineering & Functional Programming?
Sim. Cada aula de Scala for Backend Engineering & Functional Programming inclui um editor de código integrado, então você escreve e executa código real direto no navegador e recebe feedback de IA instantaneamente — nenhuma configuração local necessária.
Todas as aulas deste curso
- Dessugar de for
- Filtrando com if
- Vários geradores
- Usando Option e Future