() translation by (you can also view the original English article)
Em um artigo anterior, aprendemos sobre os Dicionários em Python e vimos como são considerados conjuntos desordenados de pares chave/valor
, onde usamos as chaves para acessar itens, ao contrário de posições, em listas, por exemplo.
Nessa dica rápida, mostremos como você pode concatenar (fundir) dois dicionários.
O Método Update()
Digamos que temos os dois dicionários abaixo:
1 |
dict1 = {'bookA': 1, 'bookB': 2, 'bookC': 3} |
2 |
dict2 = {'bookC': 2, 'bookD': 4, 'bookE': 5} |
Como podemos fundir os dois dicionários em um só? Podemos usar a função update([other])
para esse fim. Como dito na documentação do Python:
Atualiza dicionário com pares chave/valor de other, sobrescrevendo chaves existentes. Retorna None
.
update()
aceita tanto outro objeto do tipo dicionário ou um iterador de pares chave/valor (como tuplas ou outros iteráveis de tamanho dois). Se pares são passados como argumento, o dicionário é atualizado com aqueles pares:d.update(red=1, blue=2)
.
Assim, para fundir os dois dicionários acima, podemos digitar o seguinte:
dict2.update(dict1)
Digamos que você digitou a declaração abaixo para visualizar os resultados:
print dict2.update(dict1)
Nesse caso, será retornado None
! Isso se dá porque a função update()
não retorna um novo dicionário. Para obter o resultado da concatenação, digite o seguinte:
print dict2
Nesse caso, você verá o seguinte resultado:
{'bookA': 1, 'bookB': 2, 'bookC': 3, 'bookD': 4, 'bookE': 5}
E se fizéssemos o seguinte?
1 |
dict1.update(dict2) |
2 |
print dict1 |
Neste caso, obteríamos o seguinte resultado:
{'bookA': 1, 'bookB': 2, 'bookC': 2, 'bookD': 4, 'bookE': 5}
Note que, no primeiro caso, dict2.update(dict1)
, atualizamos dict2
com os pares chave/valor de dict1
e sobrescrevemos os pré-existentes nele: A chave existente, como percebemos, é 'bookC'
, que terá o valor 3
nesse caso, já que estamos atualizando com os pares chave/valor vindos de dict1
. Acontecerá o contrário no segundo caso, dict1.update(dict2)
, onde atualizaremos dict1
com os pares chave/valor de dict2
.
Entretanto, há um problema ao usar update()
para fundir dois dicionários. O problema está no fato do dicionário original ser modificado. Em outras palavras, no primeiro caso, por exemplo, dict2.update(dict1)
, a versão original de dict2
seria modificada, e no segundo caso, dict1.update(dict2)
, a versão original de dict1
seria modificada. Isso quer dizer que podemos usar update()
para fundir dois dicionários se não precisarmos manter a versão original do dicionário que queremos atualizar. Por versão original, quero dizer manter o par chave/valor.
Fundindo Dois Dicionário em uma Única Expressão
Outro método que podemos usar para fundir dois dicionários, podendo fazê-lo em uma única expressão, é o seguinte:
print dict(dict2, **dict1)
O retorno dessa declaração é:
{'bookA': 1, 'bookB': 2, 'bookC': 3, 'bookD': 4, 'bookE': 5}
Assim, dict1
sobrescreve dict2
. Se quisermos que dict2
sobrescreva dict1
, digitamos:
print dict(dict1, **dict2)
O retorno, nesse caso, seria:
{'bookA': 1, 'bookB': 2, 'bookC': 2, 'bookD': 4, 'bookE': 5}
Mantendo Valores de Chaves
Retornando ao problema sobre manter valores de chaves, como podemos fundir dois dicionários e manter os valores originais de cada um?
Um saída para isso pode ser a seguinte (obtida de uma resposta nesse tópico do StackOverflow):
1 |
from itertools import chain |
2 |
from collections import defaultdict |
3 |
dict1 = {'bookA': 1, 'bookB': 2, 'bookC': 3} |
4 |
dict2 = {'bookC': 2, 'bookD': 4, 'bookE': 5} |
5 |
dict3 = defaultdict(list) |
6 |
for k, v in chain(dict1.items(), dict2.items()): |
7 |
dict3[k].append(v) |
8 |
|
9 |
for k, v in dict3.items(): |
10 |
print(k, v) |
O retorno seria esse, nesse caso:
1 |
('bookA', [1]) |
2 |
('bookB', [2]) |
3 |
('bookC', [3, 2]) |
4 |
('bookD', [4]) |
5 |
('bookE', [5]) |
Como pode ver nessa dica rápida, é muito fácil fundir dois dicionários usando Python, mas fica bem complicado se quisermos manter os valores de chaves iguais de cada dicionário.