A partir da versão 1.18 do Go, FINALMENTE temos o generics disponível para utilização. Em outros posts, que vou deixar aqui em baixo, já abordamos como utilizar generics em funções, como utilizar a contraint comparable e fizemos um pequeno benchmark para ver a diferença com funções comuns.
Essa semana enquanto fuçava no código fonte do Go, descobri que também podemos utilizar essa maravilha em structs.
Para demonstrar como utiliza-lo, vamos criar uma struct para fazer cache das structs PessoaFisica e PessoaJuridica.
Antes de continuar, vamos criar as structs que serão armazenadas em cache.
type Pessoa struct {
Nome string
Documento string
}
type PessoaFisica struct {
Pessoa
Idade uint8
}
type PessoaJuridica struct {
Pessoa
RazaoSocial string
}
Agora que definimos as structs onde os dados serão armazenados, vamos criar uma struct genérica que possa ser usada para fazer cache tanto de PessoaFisica quanto de PessoaJuridica.
type Cache[V PessoaFisica | PessoaJuridica] struct {
data map[string]V
}
Tendo definido nosso atributo data como privado, vamos implementar dois métodos para que possamos manipular os dados do nosso cache.
O primeiro método será responsável por adicionar novos itens ou substituir itens já armazenados no cache.
func (c *Cache[V]) Set(key string, value V) {
if c.data == nil {
c.data = make(map[string]V)
}
c.data[key] = value
}
Já o segundo será responsável por retornar um dado armazenado no cache.
func (c *Cache[V]) Get(key string) (v V) {
if c.data == nil {
return
}
if v, ok := c.data[key]; ok {
return v
}
return
}
Notem que em ambos os métodos precisamos passar o Cache[V] ao invés do Cache, como fazemos normalmente.
Para testar, vamos implementar a função main com:
- Um cache para
PessoaFisicae outro paraPessoaJuridica; - Um dado de
PessoaFisicae outro dePessoaJuridica; - Armazenar os dados em seus respectivos caches;
- Retornar os dados armazenados.
func main() {
pf := PessoaFisica{
Pessoa{"Tiago", "000.000.000-00"},
32,
}
cachepf := Cache[PessoaFisica]{}
cachepf.Set(pf.Documento, pf)
pj := PessoaJuridica{
Pessoa{"Aprenda Golang LTDA", "00.000.000/0000-00"},
"Aprenda Golang",
}
cachepj := Cache[PessoaJuridica]{}
cachepj.Set(pj.Documento, pj)
fmt.Println(cachepf.Get("000.000.000-00"))
fmt.Println(cachepf.Get("000.000.110-00"))
fmt.Println("-------")
fmt.Println(cachepj.Get("00.000.000/0000-00"))
fmt.Println(cachepj.Get("00.000.000/0000-01"))
}
Como podemos ver no código acima, ao iniciar a struct é preciso passar qual será seu tipo.
Para testar é só executar um go run main.go. O resultado deve ser algo similar a isso:
{{Tiago 000.000.000-00} 32}
{{ } 0}
-------
{{Aprenda Golang LTDA 00.000.000/0000-00} Aprenda Golang}
{{ } }
Deixem suas dúvidas nos comentários.
Até a próxima!
Faça parte da comunidade!
Receba os melhores conteúdos sobre Go, Kubernetes, arquitetura de software, Cloud e esteja sempre atualizado com as tendências e práticas do mercado.

