resueltos recorrer lista elementos ejercicios diccionarios diccionario dentro anidados agregar python python-2.7 dictionary iterable-unpacking

python - recorrer - ¿Por qué un diccionario puede desempaquetarse como una tupla?



lista de diccionarios python (5)

Cuando están en contexto iterable, los dicts se tratan como una colección de claves (no ordenadas), que es lo que obtienes cuando haces una list(some_dict) , que es lo mismo que llamar a keys() en el dict:

>>> d = {''a'': 3, ''b'': 5} >>> list(d) [''a'', ''b''] >>> d.keys() [''a'', ''b'']

Sin embargo, también puedes hacer más.

Puede descomprimir tanto las claves como los valores de un dict si primero lo convierte en una lista de pares:

>>> d = {''a'': 3, ''b'': 5} >>> d_pairs = d.items() >>> print d_pairs [(''a'', 3), (''b'', 5)] >>> ((k1, v1), (k2, v2)) = d_pairs >>> print k1, v1, k2, v2 a 3 b 5

o si solo quieres los pares

>>> p1, p2 = d_pairs >>> print p1, p2 (''a'', 3) (''b'', 5)

o, digamos, solo las teclas:

>>> ((k1, _), (k2, _)) = d_pairs >>> print k1, k2 a b

etc.

Pero, por supuesto, dado que los diccionarios -y me refiero en general, no solo en Python- contienen sus artículos sin orden, items() (en Python) también los devolverá en un orden aparentemente arbitrario, y por lo tanto no hay forma de hacerlo. para saber qué clave se almacenará en qué variable:

>>> ((k1, v1), (k2, v2)) = {''bar'': 3, ''foo'': 5}.items() >>> print k1, v1, k2, v2 foo 5 bar 3

Como puede ver, el orden de los pares devueltos por items() se invirtió en comparación con su orden de definición.

Hoy, vi una declaración que no arrojó una excepción. ¿Alguien puede explicar la teoría detrás de esto?

>>> x, y = {''a'': 2, ''b'': 5} >>> x ''a'' >>> y ''b''


En Python, cada iterable se puede desempaquetar 1 :

>>> x,y,z = [1, 2, 3] # A list >>> x,y,z (1, 2, 3) >>> x,y,z = 1, 2, 3 # A tuple >>> x,y,z (1, 2, 3) >>> x,y,z = {1:''a'', 2:''b'', 3:''c''} # A dictionary >>> x,y,z (1, 2, 3) >>> x,y,z = (a for a in (1, 2, 3)) # A generator >>> x,y,z (1, 2, 3) >>>

Además, debido a que la iteración sobre un diccionario devuelve solo sus claves:

>>> for i in {1:''a'', 2:''b'', 3:''c''}: ... print i ... 1 2 3 >>>

al desempaquetar un diccionario (que lo itera) también descomprime solo sus claves.

1 En realidad, debería decir que cada iterable se puede desempaquetar siempre que los nombres para descomprimir sean iguales a la longitud del iterable:

>>> a,b,c = [1, 2, 3] # Number of names == len(iterable) >>> >>> a,b = [1, 2, 3] # Too few names Traceback (most recent call last): File "<stdin>", line 1, in <module> ValueError: too many values to unpack (expected 2) >>> >>> a,b,c,d = [1, 2, 3] # Too many names Traceback (most recent call last): File "<stdin>", line 1, in <module> ValueError: need more than 3 values to unpack >>>

Pero este es solo el caso de Python 2.x. En Python 3.x, ha ampliado el desempaquetado iterable , que le permite descomprimir un iterable de cualquier tamaño (finito) en solo los nombres que necesita:

>>> # Python 3.x interpreter ... >>> a, *b, c = [1, 2, 3, 4] >>> a, b, c (1, [2, 3], 4) >>> >>> a, *b = [1, 2, 3, 4] >>> a, b (1, [2, 3, 4]) >>> >>> *a, b, c = [1, 2, 3, 4] >>> a, b, c ([1, 2], 3, 4) >>>


Iterar un dict itera sobre las teclas. Dado que tu dict literal tiene exactamente dos teclas, puedes descomprimirla en una 2-tupla.

Probablemente esta no sea una buena práctica en general, ya que los dicts no están ordenados y x == ''b'' e y == ''a'' serían un resultado legal perfecto de ese código.


No hay ciencia de cohetes detrás de esto. dict es un iterable, que devuelve las claves en cada iteración. tuple() puede recibir cualquier iterable como argumento (siempre que sean finitos), entonces:

>>>tuple({''a'': 2, ''b'': 5}) (''a'',''b'')

Al ver esto, es fácil deducir que el desempaquetado funcionará como se muestra. Además, cualquier iterable finito puede ser desempaquetado:

>>> i = iter(range(3)) >>> a,b,c = i >>> a,b,c (0, 1, 2)


cuando iteras sobre un diccionario, obtienes sus claves

data = {''a'': 2, ''b'': 5} for key in data: print key

Desempaquetar no es más que iterar sobre el objeto y poner los elementos en las variables dadas:

keys = tuple(data) # gives (''a'', ''b'') x, y = (''a'', ''b'')