Padrão Builder em Kotlin: guia passo a passo com código

Treinador Online de Python para Iniciantes

Aprenda Python facilmente sem sobrecarga teórica. Resolva tarefas práticas com verificação automática e escreva código diretamente no navegador.

Start Course

Por que o Builder em Kotlin não é apenas um "copia e cola" do Java?



Se você já programou em Java, certamente já se deparou com o clássico padrão Builder. Dezenas de linhas de código, classes estáticas internas, métodos set e o final build(). Tudo isso funciona, mas parece verboso.



Agora imagine que você migrou para Kotlin. Uma linguagem criada para ser concisa e expressiva. E então você se depara com a tarefa: precisa criar um objeto com muitos parâmetros, alguns dos quais opcionais. Sua mão já quer escrever o Builder clássico do Java...



Pare! Em Kotlin, esse padrão pode ser implementado de forma 10 vezes mais simples, elegante e segura. Neste artigo, vamos explorar 4 maneiras de implementar o padrão Builder em Kotlin — desde a mais simples até a abordagem avançada com DSL.



Este material é baseado em uma pergunta real do Stack Overflow, que acumulou milhares de visualizações. Nós a adaptamos para conteúdo educacional, para que você possa aplicar o conhecimento imediatamente na prática.



Problema: quando o Builder é necessário?



Imagine que você tem uma classe Pizza:



class Pizza(    val size: String,    val cheese: Boolean = false,    val pepperoni: Boolean = false,    val mushrooms: Boolean = false,    val olives: Boolean = false,    val extraCheese: Boolean = false)


Até parece tudo bem. Mas quando você cria uma pizza com 5 parâmetros opcionais, o código se torna ilegível:



val pizza = Pizza("Large", true, false, true, false, true)


Ficar procurando com os olhos qual parâmetro significa o quê é angustiante. É aí que o padrão Builder vem ao resgate.



Método 1. Builder clássico estilo Java (para compatibilidade)



Se você precisa manter compatibilidade com código Java ou deseja uma API explicitamente clara, pode usar a abordagem clássica:



class Pizza private constructor(    val size: String,    val cheese: Boolean,    val pepperoni: Boolean,    val mushrooms: Boolean,    val olives: Boolean,    val extraCheese: Boolean) {    class Builder(private val size: String) {        private var cheese: Boolean = false        private var pepperoni: Boolean = false        private var mushrooms: Boolean = false        private var olives: Boolean = false        private var extraCheese: Boolean = false

fun cheese(value: Boolean) = apply { cheese = value } fun pepperoni(value: Boolean) = apply { pepperoni = value } fun mushrooms(value: Boolean) = apply { mushrooms = value } fun olives(value: Boolean) = apply { olives = value } fun extraCheese(value: Boolean) = apply { extraCheese = value }

fun build() = Pizza(size, cheese, pepperoni, mushrooms, olives, extraCheese) }}

// Uso:val pizza = Pizza.Builder("Large") .cheese(true) .pepperoni(true) .mushrooms(true) .build()


Prós: código óbvio, compreensível para desenvolvedores Java.
Contras: muito código boilerplate, não aproveita os recursos do Kotlin.



Método 2. Estilo Kotlin com argumentos nomeados e valores padrão



A maneira mais simples e frequentemente a melhor é não usar Builder, mas sim confiar nos recursos da própria linguagem:



data class Pizza(    val size: String,    val cheese: Boolean = false,    val pepperoni: Boolean = false,    val mushrooms: Boolean = false,    val olives: Boolean = false,    val extraCheese: Boolean = false)

// Uso:val pizza = Pizza( size = "Large", cheese = true, pepperoni = true, mushrooms = true)


Isso é um código limpo, legível e type-safe. Os argumentos nomeados do Kotlin resolvem o problema de "números mágicos" e da ordem dos parâmetros.



Blogs

Book Recommendations