2012-05-30 15 views
6

En Python, estoy escribiendo en un archivo de texto con un código como:Escritura de texto con un formato agradable en Python

f.write(filename + type + size + modified) 

Y, por supuesto, la salida se ve muy fea:

C:/Config/ControlSet/__db.006 file   56 KB 2012-Apr-30 10:00:46.467 AM 
C:/Config/ControlSet dir  68881 KB 2012-Apr-30 10:00:46.396 AM 
C:/Config/DataStore.avlocate file   0 KB 2012-Apr-30 09:57:42.440 AM 
C:/Config/DataStoreLocate.bak file   0 KB 2012-Apr-30 09:57:42.470 AM 
C:/Config/DeviceConnections/devconn.bak file   41 KB 2012-Apr-30 10:39:50.181 AM 
C:/Config/DeviceConnections/devconn.cfg file   41 KB 2012-May-29 10:12:45.288 AM 

Pero quiero para alinear las entradas por lo que se ve así:

C:/Config/ControlSet/__db.006           file   56 KB 2012-Apr-30 10:00:46.467 AM 
C:/Config/ControlSet              dir  68881 KB 2012-Apr-30 10:00:46.396 AM 
C:/Config/DataStore.avlocate            file   0 KB 2012-Apr-30 09:57:42.440 AM 
C:/Config/DataStoreLocate.bak           file   0 KB 2012-Apr-30 09:57:42.470 AM 
C:/Config/DeviceConnections/devconn.bak         file   41 KB 2012-Apr-30 10:39:50.181 AM 
C:/Config/DeviceConnections/devconn.cfg         file   41 KB 2012-May-29 10:12:45.288 AM 

Mi problema es similar a this question excepto que no sé cómo siempre los nombres de los archivos serán de antemano. ¿Cómo debería abordar esto?

Respuesta

19

Si usted puede obtener una lista de todos los nombres de archivo en primer lugar, entonces se podría hacer algo como:

max_width = max(len(filename) for filename in filenames) 
for filename in filenames: 
    f.write(filename.ljust(max_width+1)+..whatever else..) 

Si no puede obtener una lista de todos los nombres de archivo en primer lugar, entonces no hay manera de asegurarse de que todo se alineará, porque no hay manera de saber si más tarde obtendrá un archivo cuyo nombre es realmente largo.

En un caso como este, sin embargo, me gustaría por lo general sólo asumir que N columnas es generalmente suficiente, para algún n, en cuyo caso sólo se puede hacer algo como:

f.write('%-40s %6s %10s %2s\n' % (filename, type, size, modified)) 
10

Creo que lo que estás buscando es el método str.ljust() y quizás str.rjust() también.

Como dice en los documentos, la cadena original se devuelve si es demasiado larga, por lo que nunca se truncarán los datos, pero tendría que averiguar los largos más largos antes de tiempo para obtener un formato realmente perfecto . Sugeriría usar solo un número razonablemente grande para los valores a menos que tenga que ser perfecto.

Algo así como ...

f.write(
    "{0} {1} {2} {3}".format(
     filename.ljust(max_filename), 
     type.rjust(max_type), 
     size.rjust(max_size), 
     modified.rjust(max_modified) 
     ) 
    ) 

haría el truco.

Cuestiones relacionadas