2013-04-01 18 views
21

Ho un dizionario PythonRaggruppamento Python chiavi del dizionario come lista e creare un nuovo dizionario con questa lista come un valore

d = {1: 6, 2: 1, 3: 1, 4: 9, 5: 9, 6: 1} 

Poiché i valori nel dizionario di cui sopra non sono unici. Voglio raggruppare le tutte le chiavi di valori unici come una lista e creare un nuovo dizionario come segue:

v = {6:[1], 1:[2, 3, 6], 9: [4, 5]} 

Nota le chiavi del nuovo dizionario v devono essere ordinati. Sto trovando difficile visualizzare e implementare questa creazione di dizionari. Per favore suggeriscimi un modo facile ed efficace per farlo.

risposta

32

Utilizzando collections.defaultdict per facilità:

from collections import defaultdict 

v = defaultdict(list) 

for key, value in sorted(d.iteritems()): 
    v[value].append(key) 

ma si può fare con una palude standard dict troppo:

v = {} 

for key, value in sorted(d.iteritems()): 
    v.setdefault(value, []).append(key) 

In Python 3, utilizzare sorted(d.items()) invece.

+1

Se si va con la defaultdict, ma non si desidera che il comportamento di "default" per continuare dopo aver inizializzato il dict, è possibile impostare l'attributo 'default_factory' su' None'. Quindi il tuo 'defaultdict' si comporterà come un normale dettato in quasi tutti i modi. – mgilson

+0

Come nota a margine, sono un grande fan del modo in cui hai ordinato gli oggetti e non i valori come sarebbe il primo istinto della maggior parte delle persone (o almeno del mio). +1. – mgilson

+0

Che cos'è la 'lista' nella seconda linea? Sembra che funzionerà semplicemente avendo 'v = defaultdict()' – clwen

10

Se non si dispone in realtà bisogno di un dict alla fine della giornata, è possibile utilizzare itertools.groupby:

from itertools import groupby 
from operator import itemgetter 

for k,v in groupby(sorted(d.items()),key=itemgetter(0)): 
    print k,list(v) 

Naturalmente, si potrebbe usare questo per costruire un dict se si voleva davvero:

{k:list(v) for k,v in groupby(sorted(d.items()),key=itemgetter(0))} 

Ma a quel punto, probabilmente stai meglio usando la soluzione predefinita di Martijn.

+0

Il tuo dizionario non funziona, e invece produce: '{1: [(1, 6)], 2: [(2, 1)], 3: [(3, 1)], 4: [(4, 9)], 5: [(5, 9)], 6: [(6, 1)]} – xApple

-1

Edilizia ordina i valori e aggiunge nel nuovo dizionario in un valore di chiave esistente, altrimenti il ​​ciclo crea una nuova chiave:

result = {} 
d = {1: 6, 2: 1, 3: 1, 4: 9, 5: 9, 6: 1} 

for i, j in sorted(d.items(), key=lambda x: x[1]): 
    if j not in result: 
     result.update({j: [i]}) 
    else: 
     result.update({j: result[j] + [i]}) 
+4

Spiega le tue risposte per favore. – Blackbam

+1

Si prega di fornire maggiori dettagli. grazie – Robert

+0

@Blackbam risposta aggiornata – Frank

Problemi correlati