Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Prática de Conjuntos em Go

Prática de Conjuntos em Go

Porque um tipo `Set` é muito útil na prática, e algumas diferentes maneiras de incorporar um tipo `Set` ao seu projeto em Go. Palestra apresentada na GopherCon Brasil 2018.

27c093d0834208f4712faaaec38c2c5c?s=128

Luciano Ramalho

September 29, 2018
Tweet

Transcript

  1. c o n s t r u ç ã o

    e u s o PRÁTICA DE CONJUNTOS Porquê e como implementar um tipo Set na linguagem Go. Luciano Ramalho @ramalhoorg
  2. OBJETIVOS 1
 Demonstrar como e porque o uso de conjuntos

    pode simplificar a lógica. 2
 Discutir alternativas para implementar coleções de tipo Set em Go. 2
  3. MOTIVAÇÃO Quando senti saudade de conjuntos 3

  4. CASO DE USO #1 4 Exibir produto se todas as

    palavras da consulta apare- cerem na descrição
  5. SOLUÇÃO SEM CONJUNTOS #1 Já escrevi código assim… 5 execução

    na ordem de O(m*n) busca em O(n) busca em O(m)
  6. SOLUÇÃO SEM CONJUNTOS #2 Assim fica mais legível… 6 execução

    na ordem de O(m*n) busca em O(n)
  7. 7 Que tal se… Depois! Agora estou muito ocupado! www.workcompass.com/

  8. CASO DE USO #1 8 Exibir produto se todas as

    palavras da consulta apare- cerem na descrição Q ⊂ D www.workcompass.com/
  9. CASO DE USO #2 9 Marcar todos os produtos favoritados,

    exceto os que já estiverem no carrinho de compras.
  10. CASO DE USO #2 10 Marcar todos os produtos favoritados,

    exceto os que já estiverem no carrinho de compras. F ∖ C
  11. CASO DE USO #3: RUNEFINDER 11 https://tgo.li/runes2018

  12. CASO DE USO #3: RUNEFINDER 12 https://tgo.li/runes2018

  13. CASO DE USO #3: RUNEFINDER 13 https://tgo.li/runes2018

  14. CASO DE USO #3: ÍNDICE INVERTIDO

  15. CASO DE USO #3: ÍNDICE INVERTIDO “REGISTERED SIGN” é o

    nome oficial de ® em UnicodeData.txt
  16. CASO DE USO #3: ÍNDICE INVERTIDO 16 www.workcompass.com/ index é

    o índice invertido: as chaves são palavras, e os valores são conjuntos de runas cujo nome contém a palavra. Ex. a runa ‘®’ aparece nas chaves “REGISTERED” e “SIGN”
  17. CASO DE USO #3: ÍNDICE INVERTIDO 17 A ∩ B

    www.workcompass.com/
  18. LÓGICA E CONJUNTOS Uma relação íntima 18

  19. Ainda não descobriram um ramo da
 matemática que não possa

    ser formalizado
 pela teoria dos conjuntos. Thomas Forster
 (tradução livre de Logic Induction and Sets, p. 167) 19
  20. CONJUNÇÃO LÓGICA: INTERSECÇÃO x pertence à intersecção de A e

    B. é o mesmo que: x pertence ao conjunto A e
 x também pertence ao conjunto B. Em notação matemática: x ∈ (A ∩ B) ⟺ (x ∈ A) ∧ (x ∈ B) Em computação: AND 20
  21. DISJUNÇÃO LÓGICA: UNIÃO x pertence à união de A e

    B. é o mesmo que: x pertence ao conjunto A e/ou
 x pertence ao conjunto B. Em notação matemática: x ∈ (A ∪ B) ⟺ (x ∈ A) ∨ (x ∈ B) Em computação: OR 21
  22. DIFERENÇA SIMÉTRICA x pertence ao conjunto A ou
 x pertence

    ao conjunto B
 mas não pertence aos dois é o mesmo que: x pertence à união de A e B menos a intersecção de A e B. Em notação matemática:
 Em computação: XOR 22 x ∈ (A ∆ B) ⟺ (x ∈ A) ⊻ (x ∈ B)
  23. DIFERENÇA x pertence ao conjunto A mas
 não pertence ao

    conjunto B. é o mesmo que: elementos de A menos os de B Em notação matemática: x ∈ (A ∖ B) ⟺ (x ∈ A) ∧ (x ∉ B) 23
  24. CONJUNTOS EM VÁRIAS LINGUAGENS 24

  25. CONJUNTOS EM VÁRIAS BIBLIOTECAS-PADRÃO Algumas linguagens/plataformas que implementam conjuntos em

    sua biblioteca-padrão. 25 Java Interface Set com < 10 métodos; 8 implementações JavaScript (ES6) Set com < 10 métodos .Net (C# etc.) Interface ISet com > 10 métodos; 2 implementações Python set e frozenset com > 10 métodos e operadores Ruby Set com > 10 métodos e operadores
  26. REINVENTANDO A RODA EM GO 26

  27. USO DE MAP COMO CONJUNTO Chaves de um map formam

    um conjunto
 com duas características essenciais: •Garantia de unicidade: 
 uma chave só pode ocorrer uma vez. •Verificação de pertencimento em O(1): 
 tempo praticamente constante independente do número de elementos.
 
 
 
 Demais métodos? Fique à vontade para implementar! 27 if _, existe := conjunto[elem]; existe { // o elemento está no conjunto }
  28. USO DE MAP COMO CONJUNTO Chaves de um map formam

    um conjunto
 com duas características essenciais: •Garantia de unicidade: 
 uma chave só pode ocorrer uma vez. •Verificação de pertencimento em O(1): 
 tempo praticamente constante independente do número de elementos.
 
 
 
 Demais métodos? Fique à vontade para implementar! 28 Curiosidade:
 era assim que a gente se virava em Python até 2003 — usando chaves de um dict como um conjunto! if _, existe := conjunto[elem]; existe { // o elemento está no conjunto }
  29. RELEMBRANDO: CASO DE USO #1 29 Exibir produto se todas

    as palavras da consulta apare- cerem na descrição Q ⊂ D www.workcompass.com/
  30. SOLUÇÃO COM MAP FAZENDO PAPEL DE CONJUNTO Solução mais eficiente

    que as anteriores, para slices grandes: 30 map de <tipo-elemento> para struct{}
  31. SOLUÇÃO COM MAP FAZENDO PAPEL DE CONJUNTO Solução mais eficiente

    que as anteriores, para slices grandes: 31 preencher o
 “conjunto”
  32. SOLUÇÃO COM MAP FAZENDO PAPEL DE CONJUNTO Solução mais eficiente

    que as anteriores, para slices grandes: 32 busca em O(1) busca em O(n)
  33. CONJUNTOS “GENÉRICOS” EM GO Elementos tipo interface{} 33

  34. GOLANG-SET By Ralph Caraveo (@deckarep) 34

  35. 35

  36. GOLANG-SET, VULGO MAPSET… 36

  37. GOLANG-SET: INTERFACE SET 37 22 métodos

  38. threadUnsafeSet threadSafeSet GOLANG-SET: IMPLEMENTAÇÕES 38 elementos tipo interface{}

  39. GOLANG-SET: EXEMPLO 39

  40. GOLANG-SET: CODE REVIEW 40

  41. GOLANG-SET: CODE REVIEW 41 elementos tipo interface{} porque?

  42. GOLANG-SET: CODE REVIEW 42

  43. GOLANG-SET: CODE REVIEW 43

  44. GODS Go Data Structures 44

  45. 45 elementos tipo interface{}

  46. GODS: PACKAGE SETS 46 interface:
 7 métodos 2 implementações: HashSest,

    TreeSet
  47. GEN Type-driven code generation for Go 47

  48. GEN: GERADOR DE CÓDIGO COM TIPOS PARAMETRIZADOS 48

  49. GEN: MODO DE USAR 1. Marque o seu código com

    comentários especiais: 
 
 
 
 
 2. Execute o comando gen 
 3. Adicione ao seu projeto o arquivo .go gerado 49 Exemplo em: https://tgo.li/2vtcMjw
  50. GEN: MEU CÓDIGO FONTE (CODEPOINTS.GO) 50 Exemplo em: https://tgo.li/2vtcMjw

  51. GEN: O ARQUIVO GERADO (CODEPOINT_SET.GO) 51 Exemplo em: https://tgo.li/2vtcMjw código

    derivado
 de golang-set
  52. CONJUNTOS ESPECIALIZADOS 52

  53. MAP COM NOME standupdev/runeset 53

  54. RUNESET: DEFINIÇÃO DO TIPO E MÉTODOS ESSENCIAIS 54 https://github.com/standupdev/runeset elementos

    do tipo rune
  55. RUNESET: CARACERÍSTICAS Não encapsula o map: pode ser acessado e

    modificado direto.
 Sintaxe melhor para criar e testar elementos: 
 Exemplo: 55 s.Add(e)
 s.Contains(e) https://github.com/standupdev/runeset
  56. RUNESET: TIPO MAP COM NOME E MÉTODOS 56 10 métodos,

    incluindo: Intersection, IntersectionUpdate
  57. RUNESET: CONSTRUTORES Convenção: Usar Make para criar objetos manipulados por

    referências. 57 https://github.com/standupdev/runeset cria um
 Set vazio
  58. MakeFromString: set de runas a partir de string RUNESET: CONSTRUTORES

    58 custo zero para passar uma slice: runas…
  59. RUNESET: INTERSECÇÃO 59 https://github.com/standupdev/runeset

  60. RUNESET: USO EM ÍNDICE INVERTIDO (CASO DE USO #3)

  61. RUNESET: MÉTODOS ÚTEIS Além de operações da teoria dos conjuntos…


    MakeFromString: construtor que aceita string.
 Sorted: devolve slice de runas em ordem ascendente String: elementos ordenados para facilitar exemplos.
 Equal: facilita muito os testes.
 Copy: importante especialmente em coleções mutáveis. 61
  62. MAP ENCAPSULADO 62

  63. STRSET: TIPO MAP ENCAPSULADO EM STRUCT 63 https://github.com/standupdev/strset

  64. STRSET: CARACTERÍSTICAS Protege o map: campo privado só pode acessado

    via métodos e funções do mesmo pacote.
 Não é prático construir com a sintaxe Set{}: 
 melhor usar Make(). 
 Exemplo: 64 https://github.com/standupdev/strset
  65. STRSET: API 65 26 métodos

  66. COMPARAR APIS PARA ESCOLHER NOMES DE MÉTODOS 66

  67. ORGANIZAÇÃO DO PACOTE STRSET Nota: todos os métodos que modificam

    um Set depois de criado estão no arquivo updaters.go. 67 core.go Make, Len, Contains, String, Equal, Copy, ToSlice, Channel operators.go Intersection, Union,
 Difference, SymmetricDifference relations.go SubsetOf, SupersetOf updaters.go Add, AddAll, Remove, RemoveAll, Pop, Clear, IntersectionUpdate, UnionUpdate, DifferenceUpdate, SymmetricDifferenceUpdate https://github.com/standupdev/strset
  68. RUNESCAN: EXEMPLO DE USO DE STRSET 68

  69. 69

  70. BÔNUS Contribuições do Vitor De Mario 70

  71. SUGESTÕES DO VITOR DE MARIO 71

  72. PROJETO SCYLLABDB GO-SET 72 https://github.com/scylladb/go-set

  73. CONCLUSÃO 73

  74. CONJUNTOS NA PRÁTICA Operações de conjunto podem simplificar sua lógica

    golang-set (@deckarep): a implementação rica mais popular gen pode produzir um golang-set específico para seu tipo Codar um tipo set é um ótimo exercício de programação Se precisar de Set para elementos string, use strset! 74 https://github.com/standupdev/strset
  75. FICÇÃO CIENTÍFICA Bom mesmo seria isso… 75 var s1 set[string]

    s2 := make(set[uint64])
  76. Luciano Ramalho
 @ramalhoorg | @standupdev
 luciano.ramalho@thoughtworks.com MUITO GRATO!