Solucionado (ver solução)
Solucionado
(ver solução)
3
respostas

Fazer um loop para encontrar respostas idênticas dentro de vários objetos de chave valor

Supondo de vários objetos de chave valor: obj_chave_valor[enúmeras posições]

In [1]: obj_chave_valor[0]
Out[1]: {
   "/envi/cce/comcce/ie/MF":[
      "Element \\'{http://www.portal.com.br/cce}MF\\': [facet \\'pattern\\'] The value \\'\\' is not accepted by the pattern \\'[0-9]{7}\\'."
   ],
   "/envi/cce/comcce/ie/UF":[
      "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\'}."
   ],
   "/envi/cce/comcce/est/MU":[
      "Element \\'{http://www.portal.com.br/cce}MU\\': [facet \\'pattern\\'] The value \\'\\' is not accepted by the pattern \\'[0-8]{2}\\'."
   ],
   "/envi/cce/comcce/est/UF":[
      "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\', \\'AY\\', \\'AM\\', \\'AP\\', \\'BA\\'}."
   ]
}
In [2]: obj_chave_valor[1]
Out[2]: {
  "/envi/cce/comcce/est/UF":[
      "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\', \\'AY\\', \\'AM\\', \\'AP\\', \\'BA\\'}."
   ]
}

In [3]: obj_chave_valor[2]
Out[3]: {
    "/envi/cce/comcce/est/MU":[
      "Element \\'{http://www.portal.com.br/cce}MU\\': [facet \\'pattern\\'] The value \\'\\' is not accepted by the pattern \\'[0-8]{2}\\'."
   ],
   "/envi/cce/comcce/est/UF":[
      "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\', \\'AY\\', \\'AM\\', \\'AP\\', \\'BA\\'}."
   ]
}

Eu sei que se eu fizer len(obj_chave_valor) eu consigo o tamanho ele (quantos índices o mesmo possui)... Mas, minha dúvida é em conseguir verificar "randomicamente", por exemplo usando um "for ou algo mais otimizado", uma vez que esses objetos podem ser grandes, verificar quais são as chaves que mais se repetem e ranqueá-las. Sei que posso conseguir contar usando um if:

if obj_chave_valor.get('/envi/cce/comcce/est/UF'):   
             cce_est_UF += 1  

Mas, no caso ilustrado, pensando que tenho várias possibilidades de chave valor, queria que meu próprio script fizesse o levantamento de:

  • todas as chaves que existem,
  • quantidade de repetição de cada chave,
  • rankear em ordem decrescente

Tentei fazer algo assim, mas não deu certo:

for key in objeto_errors:
    if objeto_errors.get('key'): 
        key += 1 
        print(key)
    print("key que teve mais quantidade de repetição:", quantidade)  

E o resultado que eu espero é:

/envi/cce/comcce/est/UF: 102
/envi/cce/comcce/est/MU: 97
/envi/cce/comcce/ie/MU: 96
/envi/cce/comcce/ie/MF: 2

Agradeço se puderem me ajudar!

3 respostas

Olá Yara, como vai?

O Counter talvez resolva seu problema. Você pode tentar da seguinte forma:

from collections import Counter

counter = Counter()                      # Inicializa um Counter vazio
for objeto in obj_chave_valor:           # Itera sobre os elementos da sua lista de dicionários
    for chave, valor in objeto.items():  # Separa cada elemento(dict) em chave/valor 
        counter += chave                 # Adiciona somente a chave ao objeto Counter
print(counter)

O resultado deverá ser o que você espera :)

Espero ter ajudado! Bons estudos.

Olá Lorran! Obrigada pela resposta, mas ainda não está funcionando.

In [21]: type(obj_chave_valor)                                                   
Out[21]: list
In [22]: from collections import Counter 
    ...:  
    ...: counter = Counter()                       
    ...: for objeto in obj_chave_valor:            
    ...:     for chave, valor in objeto.items():  
    ...:         counter += chave                  
    ...: print(counter) 
    ...:  
    ...:                                                                        
---------------------------------------------------------------------------
AttributeError                                  Traceback (most recent call last)
/opt/yara/const.py in <module>
      2 
      3 counter = Counter()
      4 for objeto in obj_chave_valor:
   ----> 5 for chave, valor in objeto.items():
      6         counter += chave

AttributeError: 'str' object has no attribute 'items'

solução!

Yara, creio que você tenha uma estrutura similar a esta:

obj_chave_valor = [
    {
        "/envi/cce/comcce/ie/MF": [
            "Element \\'{http://www.portal.com.br/cce}MF\\': [facet \\'pattern\\'] The value \\'\\' is not accepted by the pattern \\'[0-9]{7}\\'."
        ],
        "/envi/cce/comcce/ie/UF":[
            "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\'}."
        ],
        "/envi/cce/comcce/est/MU":[
            "Element \\'{http://www.portal.com.br/cce}MU\\': [facet \\'pattern\\'] The value \\'\\' is not accepted by the pattern \\'[0-8]{2}\\'."
        ],
        "/envi/cce/comcce/est/UF":[
            "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\', \\'AY\\', \\'AM\\', \\'AP\\', \\'BA\\'}."
        ]
    },
    {
        "/envi/cce/comcce/est/UF": [
            "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\', \\'AY\\', \\'AM\\', \\'AP\\', \\'BA\\'}."
        ]
    },
    {
        "/envi/cce/comcce/est/MU": [
            "Element \\'{http://www.portal.com.br/cce}MU\\': [facet \\'pattern\\'] The value \\'\\' is not accepted by the pattern \\'[0-8]{2}\\'."
        ],
        "/envi/cce/comcce/est/UF":[
            "Element \\'{http://www.portal.com.br/cce}UF\\': [facet \\'enumeration\\'] The value \\'n/a\\' is not an element of the set {\\'AC\\', \\'AY\\', \\'AM\\', \\'AP\\', \\'BA\\'}."
        ]
    }
]

Sendo assim, utilize o Counter da seguinte forma:

counter = Counter()

for i in range(len(obj_chave_valor)):
    for objeto in obj_chave_valor[i]:
        counter[objeto] += 1

for chave, valor in counter.items():
    print(chave, valor)

Resultado:

/envi/cce/comcce/ie/MF 1
/envi/cce/comcce/ie/UF 1
/envi/cce/comcce/est/MU 2
/envi/cce/comcce/est/UF 3

O Counter faz parte das Collections do Python e ele irá guardar em um dicionário a contagem de cada uma das chaves da sua lista :) Você pode ver mais detalhes a respeito dele na documentação.

Abraços e bons estudos!