PauloRB.dev

Desenvolvedor de Software

Estruturas de Dados em Go: Guia Simples com Exemplos Práticos | PauloRB.dev Estruturas de Dados em Go: Guia Simples com Exemplos Práticos – PauloRB.dev
Estruturas de Dados em Go: Guia Simples com Exemplos Práticos

Estruturas de Dados em Go: Guia Simples com Exemplos Práticos

Go (ou Golang) é uma linguagem de programação eficiente e fácil de usar, conhecida por sua simplicidade, sendo ideal para construir sistemas escaláveis e de alto desempenho. Neste post, vamos explorar as principais estruturas de dados em Go com exemplos práticos, mostrando como aplicá-las no dia a dia de um desenvolvedor.

Arrays

Arrays em Go são de tamanho fixo e armazenam elementos do mesmo tipo. Eles são úteis quando sabemos previamente o número exato de elementos.

package main

import "fmt"

func main() {
    var numeros [5]int
    numeros[0] = 1
    numeros[1] = 2
    fmt.Println(numeros) // Saída: [1 2 0 0 0]
}

Slices

Slices são usados para armazenar uma sequência dinâmica de elementos e são muito mais comuns que arrays. A principal vantagem dos slices é que eles podem crescer ou encolher conforme necessário.

package main

import "fmt"

func main() {
    numeros := []int{1, 2, 3}
    numeros = append(numeros, 4, 5)
    fmt.Println(numeros) // Saída: [1 2 3 4 5]
}

Mapas (Maps)

Mapas são uma estrutura de dados que associa chaves a valores, como um dicionário.

package main

import "fmt"

func main() {
    capitais := map[string]string{
        "Brasil": "Brasília",
        "França": "Paris",
    }
    capitais["Japão"] = "Tóquio"
    fmt.Println(capitais) // Saída: map[Brasil:Brasília França:Paris Japão:Tóquio]
}

Structs

Structs são a maneira de criar tipos compostos em Go, agrupando diferentes dados em uma única entidade.

package main

import "fmt"

type Pessoa struct {
    Nome  string
    Idade int
}

func main() {
    pessoa := Pessoa{Nome: "João", Idade: 30}
    fmt.Println(pessoa) // Saída: {João 30}
}

Filas (Queues)

Uma fila é uma estrutura de dados onde o primeiro elemento inserido é o primeiro a ser removido (FIFO – First In, First Out). Um exemplo prático de fila é o gerenciamento de tarefas, como em sistemas de mensagens ou processamento de jobs.

Em Go, podemos implementar uma fila simples usando slices:

package main

import "fmt"

type Queue []int

func (q *Queue) Enqueue(valor int) {
    *q = append(*q, valor)
}

func (q *Queue) Dequeue() int {
    valor := (*q)[0]
    *q = (*q)[1:]
    return valor
}

func main() {
    fila := Queue{}
    fila.Enqueue(10)
    fila.Enqueue(20)
    fmt.Println(fila) // Saída: [10 20]
    primeiro := fila.Dequeue()
    fmt.Println(primeiro) // Saída: 10
    fmt.Println(fila)     // Saída: [20]
}

Aqui, criamos uma fila simples que permite enfileirar (adicionar) e desenfileirar (remover) elementos. Essa estrutura é útil em sistemas onde as tarefas precisam ser processadas na ordem em que foram recebidas.

Pilhas (Stacks)

Pilhas são uma estrutura de dados onde o último elemento inserido é o primeiro a ser removido (LIFO – Last In, First Out). Elas são úteis em problemas como análise de expressões ou navegação entre páginas (ex: histórico de páginas).

package main

import "fmt"

type Stack []int

func (s *Stack) Push(valor int) {
    *s = append(*s, valor)
}

func (s *Stack) Pop() int {
    index := len(*s) - 1
    valor := (*s)[index]
    *s = (*s)[:index]
    return valor
}

func main() {
    pilha := Stack{}
    pilha.Push(10)
    pilha.Push(20)
    fmt.Println(pilha) // Saída: [10 20]
    ultimo := pilha.Pop()
    fmt.Println(ultimo) // Saída: 20
    fmt.Println(pilha)  // Saída: [10]
}

Árvores Binárias

As árvores binárias são uma estrutura de dados que organizam informações de forma hierárquica. Cada nó tem, no máximo, dois filhos. Elas são muito usadas para criar algoritmos eficientes de busca e ordenação.

Um exemplo básico de árvore binária:

package main

import "fmt"

type Node struct {
    Valor int
    Esquerda, Direita *Node
}

func (n *Node) Inserir(valor int) {
    if valor < n.Valor {
        if n.Esquerda == nil {
            n.Esquerda = &Node{Valor: valor}
        } else {
            n.Esquerda.Inserir(valor)
        }
    } else {
        if n.Direita == nil {
            n.Direita = &Node{Valor: valor}
        } else {
            n.Direita.Inserir(valor)
        }
    }
}

func (n *Node) Buscar(valor int) bool {
    if n == nil {
        return false
    }
    if n.Valor == valor {
        return true
    } else if valor < n.Valor {
        return n.Esquerda.Buscar(valor)
    } else {
        return n.Direita.Buscar(valor)
    }
}

func main() {
    raiz := &Node{Valor: 10}
    raiz.Inserir(5)
    raiz.Inserir(15)
    raiz.Inserir(8)
    
    fmt.Println(raiz.Buscar(8))  // Saída: true
    fmt.Println(raiz.Buscar(100)) // Saída: false
}

Neste exemplo, implementamos uma árvore binária de busca (BST), onde valores menores que o nó atual vão para a esquerda, e valores maiores, para a direita. Isso permite fazer buscas eficientes.

Conclusão

As estruturas de dados são fundamentais para criar soluções eficientes. Em Go, podemos usar arrays, slices, mapas, structs, filas, pilhas e árvores binárias de forma simples e prática. Cada uma dessas estruturas tem seu uso específico e podem ser aplicadas em diversas situações do dia a dia de um desenvolvedor.

Para saber mais sobre essas e outras estruturas de dados em Go, recomendo explorar a documentação oficial e o livro The Go Programming Language, que aprofunda os conceitos de Go.

Essas estruturas ajudam a organizar dados de forma eficiente, melhorando a performance de suas aplicações e facilitando o desenvolvimento de algoritmos robustos.

Mais Posts

Como acessar o entity Manager(Doctrine) dentro de comandos no Symfony 5

Como acessar o entity Manager(Doctrine) dentro de comandos no Symfony 5

Ao termos de criar comandos personalizados no Symfony na maioria das vezes se faz necessário o uso de alguma interação... Leia mais

Script para automatizar as instalações de extensões do php em distribuições LINUX

Script para automatizar as instalações de extensões do php em distribuições LINUX

Publiquei neste artigo https://paulorb.dev/alternar-entre-multiplas-versoes-no-php/ formas de como instalar diversas versões do PHP em distros Linux mas surgiu um problema que... Leia mais

Por que whereNull não funciona com updateOrCreate no Laravel (e como evitar bugs silenciosos)

Por que whereNull não funciona com updateOrCreate no Laravel (e como evitar bugs silenciosos)

O updateOrCreate() é um dos métodos mais utilizados no Eloquent para garantir que registros sejam atualizados ou criados sem duplicações.... Leia mais

Tutorial: Exportando Imagens Base64 Usando Laravel Excel

Tutorial: Exportando Imagens Base64 Usando Laravel Excel

Neste tutorial, vamos aprender como exportar uma lista de cadastros de clientes para uma planilha Excel, incluindo as fotos dos... Leia mais