2009-12-17 17 views
9

Tengo un proyecto de conversión de una base de datos a otra. Una de las columnas de la base de datos original define la categoría de la fila. Esta columna debe asignarse a una nueva categoría en la nueva base de datos.Mapeo uno a uno de Python (creación de clases de equivalencia)

Por ejemplo, vamos a suponer las categorías originales son: parrot, spam, cheese_shop, Cleese, Gilliam, Palin

Ahora que es un poco más detallado para mí, y yo quiero tener estas filas categorizados como sketch, actor - es decir, definir todos los bocetos y todos los actores como dos clases de equivalencia.

>>> monty={'parrot':'sketch', 'spam':'sketch', 'cheese_shop':'sketch', 
'Cleese':'actor', 'Gilliam':'actor', 'Palin':'actor'} 
>>> monty 
{'Gilliam': 'actor', 'Cleese': 'actor', 'parrot': 'sketch', 'spam': 'sketch', 
'Palin': 'actor', 'cheese_shop': 'sketch'} 

que es bastante awkward- yo preferiría tener algo como:

monty={ ('parrot','spam','cheese_shop'): 'sketch', 
     ('Cleese', 'Gilliam', 'Palin') : 'actors'} 

Pero esto, por supuesto, pone toda la tupla como clave:

>>> monty['parrot'] 

Traceback (most recent call last): 
    File "<pyshell#29>", line 1, in <module> 
    monty['parrot'] 
KeyError: 'parrot' 

Alguna idea de cómo crear un diccionario elegante de muchos a uno en Python?

Gracias,

Adam

+1

Mira esta elegante [respuesta] (http://stackoverflow.com/a/11105962/355230) a una pregunta similar. – martineau

Respuesta

11

Me parece que tiene dos preocupaciones. En primer lugar, ¿cómo se expresa originalmente su mapeo, es decir, cómo se escribe la asignación en su archivo new_mapping.py? En segundo lugar, ¿cómo funciona la asignación durante el proceso de reasignación de mapas? No hay ninguna razón para que estas dos representaciones sean iguales.

de inicio con el mapeo en el que quieres:

monty = { 
    ('parrot','spam','cheese_shop'): 'sketch', 
    ('Cleese', 'Gilliam', 'Palin') : 'actors', 
} 

entonces convertirlo en el mapeo que necesita:

working_monty = {} 
for k, v in monty.items(): 
    for key in k: 
     working_monty[key] = v 

producción:

{'Gilliam': 'actors', 'Cleese': 'actors', 'parrot': 'sketch', 'spam': 'sketch', 'Palin': 'actors', 'cheese_shop': 'sketch'} 

a continuación, utilizar working_monty para hacer el trabajo .

+1

+1 Muchas gracias. Supongo que no hay un tipo nativo de Python para este trabajo; ¿Crees que debería haber uno? –

+0

¿No podemos tener alguna referencia como el valor en el par (clave, valor) en lugar de almacenar la cadena real? Desde el no. de teclas son significativamente más grandes que el no. de valores, esto ahorraría mucho espacio. ¿Hay alguna forma de hacer esto? – ishan3243

1
>>> monty={ ('parrot','spam','cheese_shop'): 'sketch', 
     ('Cleese', 'Gilliam', 'Palin') : 'actors'} 

>>> item=lambda x:[z for y,z in monty.items() if x in y][0] 
>>> 
>>> item("parrot") 
'sketch' 
>>> item("Cleese") 
'actors' 

Pero déjeme decirle, será lento que uno normal a un diccionario.

+0

Lento, pero en el lado positivo no requiere una estructura de datos secundaria persistente. Podría acelerarse un cierto grado al no estar escrito como un lambda y usar una lista de comprensión. – martineau

4

Se podría anular indexador de dict, pero tal vez la siguiente solución más simple sería mejor: (. Tal vez el anidado de bucle se puede comprimir una impresionante de una sola línea, pero esto funciona y es legible)

>>> assoc_list = ((('parrot','spam','cheese_shop'), 'sketch'), (('Cleese', 'Gilliam', 'Palin'), 'actors')) 
>>> equiv_dict = dict() 
>>> for keys, value in assoc_list: 
    for key in keys: 
     equiv_dict[key] = value 


>>> equiv_dict['parrot'] 
'sketch' 
>>> equiv_dict['spam'] 
'sketch' 

+1

No es para corazones débiles: equiv_dict = dict (suma ([[(k, v) para k en ks] para (ks, v) en assoc_list], [])) –

0

Si usted quiere tener varias claves que apuntan al mismo valor, es decir

m_dictionary{('k1', 'k2', 'k3', 'k4'):1, ('k5', 'k6'):2} y acceder a ellos como,

`print(m_dictionary['k1'])` ==> `1`. 

Comprobar este multi diccionario módulo de Python multi_key_dict. Instalar e Importarlo. https://pypi.python.org/pypi/multi_key_dict

Cuestiones relacionadas