Pregunta Python: escribir un diccionario en un archivo csv con una línea por cada 'clave: valor'


Tengo un diccionario:

mydict = {key1: value_a, key2: value_b, key3: value_c}

Quiero escribir los datos en un archivo dict.csv, en este estilo:

key1: value_a
key2: value_b
key3: value_c

Escribí:

import csv
f = open('dict.csv','wb')
w = csv.DictWriter(f,mydict.keys())
w.writerow(mydict)
f.close()

Pero ahora tengo todas las llaves en una fila y todos los valores en la siguiente fila.

Cuando logro escribir un archivo como este, también quiero leerlo en un nuevo diccionario.

Solo para explicar mi código, el diccionario contiene valores y bools de textctrls y checkboxes (usando wxpython). Quiero agregar los botones "Guardar configuraciones" y "Cargar configuraciones". La configuración de guardar debe escribir el diccionario en el archivo de la manera mencionada (para que sea más fácil para el usuario editar el archivo csv directamente), cargar la configuración debe leer el archivo y actualizar los cuadros de texto y las casillas de verificación.


58
2017-12-31 02:06


origen


Respuestas:


los DictWriter no funciona de la manera que esperas

with open('dict.csv', 'wb') as csv_file:
    writer = csv.writer(csv_file)
    for key, value in mydict.items():
       writer.writerow([key, value])

Para leerlo de nuevo:

with open('dict.csv', 'rb') as csv_file:
    reader = csv.reader(csv_file)
    mydict = dict(reader)

que es bastante compacto, pero supone que no necesita hacer ninguna conversión de tipo al leer


130
2017-12-31 02:22



La forma más sencilla es ignorar el módulo csv y formatearlo usted mismo.

with open('my_file.csv', 'w') as f:
    [f.write('{0},{1}\n'.format(key, value)) for key, value in my_dict.items()]

9
2017-11-02 05:29



Solo para dar una opción, escribir un diccionario en un archivo csv también podría hacerse con el paquete pandas. Con el ejemplo dado, podría ser algo como esto:

mydict = {'key1': 'a', 'key2': 'b', 'key3': 'c'}

import pandas as pd

(pd.DataFrame.from_dict(data=mydict, orient='index')
   .to_csv('dict_file.csv', header=False))

Lo más importante a tener en cuenta es establecer el parámetro 'orientar' a 'índice' dentro del from_dict método. Esto le permite elegir si desea escribir cada clave del diccionario en una nueva fila.

Adicionalmente, dentro del to_csv método el parámetro del encabezado se establece en False solo para tener solo los elementos del diccionario sin filas molestas. Siempre puede establecer los nombres de columna e índice dentro del método to_csv

Su salida se vería así:

key1,a
key2,b
key3,c

Si, por el contrario, quiere que las claves sean los nombres de las columnas, simplemente use el parámetro predeterminado 'orientar' que es 'columnas', como podría verificar en los enlaces de documentación.


5
2017-08-03 00:02



outfile = open( 'dict.txt', 'w' )
for key, value in sorted( mydict.items() ):
    outfile.write( str(key) + '\t' + str(value) + '\n' )

3
2017-09-25 12:21



¿Puedes hacer lo siguiente?

for key in mydict.keys():
    f.write(str(key) + ":" + str(mydict[key]) + ",");

Para que puedas tener

key_1: value_1, key_2: value_2


2
2017-12-31 02:13



Personalmente siempre he encontrado que el módulo csv es algo molesto. Espero que alguien más te muestre cómo hacer esto con cuidado, pero mi solución rápida y sucia es:

with open('dict.csv', 'w') as f:  # This creates the file object for the context 
                                  # below it and closes the file automatically
    l = []
    for k, v in mydict.iteritems(): # Iterate over items returning key, value tuples
        l.append('%s: %s' % (str(k), str(v))) # Build a nice list of strings
    f.write(', '.join(l))                     # Join that list of strings and write out

Sin embargo, si quieres volver a leerlo, necesitarás hacer algunos análisis irritantes, especialmente si todo está en una línea. Aquí hay un ejemplo usando su formato de archivo propuesto.

with open('dict.csv', 'r') as f: # Again temporary file for reading
    d = {}
    l = f.read().split(',')      # Split using commas
    for i in l:
        values = i.split(': ')   # Split using ': '
        d[values[0]] = values[1] # Any type conversion will need to happen here

1
2017-12-31 02:24