Los pandas crean marcos de datos vacíos con solo nombres de columna

151

Tengo un DataFrame dinámico que funciona bien, pero cuando no hay datos para agregar al DataFrame, aparece un error. Y, por lo tanto, necesito una solución para crear un DataFrame vacío con solo los nombres de columna.

Por ahora tengo algo como esto:

df = pd.DataFrame(columns=COLUMN_NAMES) # Note that there are now row data inserted.

PD: es importante que los nombres de columna sigan apareciendo en un DataFrame.

Pero cuando lo uso así obtengo algo así como resultado:

Index([], dtype='object')
Empty DataFrame

¡La parte "Empty DataFrame" es buena! Pero en lugar de lo del índice, todavía necesito mostrar las columnas.

Editar:

Una cosa importante que descubrí: estoy convirtiendo este DataFrame a PDF usando Jinja2, por lo tanto, estoy llamando a un método para primero enviarlo a HTML de esta manera:

df.to_html()

Aquí es donde las columnas se pierden, creo.

Edit2: en general, seguí este ejemplo: http://pbpython.com/pdf-reports.html . El CSS también es del enlace. Eso es lo que hago para enviar el marco de datos al PDF:

env = Environment(loader=FileSystemLoader('.'))
template = env.get_template("pdf_report_template.html")
template_vars = {"my_dataframe": df.to_html()}

html_out = template.render(template_vars)
HTML(string=html_out).write_pdf("my_pdf.pdf", stylesheets=["pdf_report_style.css"])

Edit3:

Si imprimo el marco de datos justo después de la creación, obtengo lo siguiente:

[0 rows x 9 columns]
Empty DataFrame
Columns: [column_a, column_b, column_c, column_d, 
column_e, column_f, column_g, 
column_h, column_i]
Index: []

Eso parece razonable, pero si imprimo el template_vars:

'my_dataframe': '<table border="1" class="dataframe">\n  <tbody>\n    <tr>\n      <td>Index([], dtype=\'object\')</td>\n      <td>Empty DataFrame</td>\n    </tr>\n  </tbody>\n</table>'

Y parece que ya faltan las columnas.

E4: si imprimo lo siguiente:

print(df.to_html())

Ya obtengo el siguiente resultado:

<table border="1" class="dataframe">
  <tbody>
    <tr>
      <td>Index([], dtype='object')</td>
      <td>Empty DataFrame</td>
    </tr>
  </tbody>
</table>
E. Muuli
fuente
¿Lo siguiente ahora funciona para ti? De lo contrario, debe proporcionar más información sobre su entorno, como la versión de Python, la versión de Pandas, etc.
Marcus V.
Estoy usando Python v3.4, Pandas v0.13.1
E. Muuli
1
Hola Eerik, no puedo reproducir lo que tienes en E4. Si hago esto, la impresión se parece a la que tengo a continuación. ¿Podrías actualizar tu versión de pandas? Porque el tuyo es bastante viejo (estoy en 0.20.1).
Marcus V.
1
¡Gracias, actualizar Pandas funcionó!
E. Muuli

Respuestas:

190

Puede crear un DataFrame vacío con nombres de columna o un Índice:

In [4]: import pandas as pd
In [5]: df = pd.DataFrame(columns=['A','B','C','D','E','F','G'])
In [6]: df
Out[6]:
Empty DataFrame
Columns: [A, B, C, D, E, F, G]
Index: []

O

In [7]: df = pd.DataFrame(index=range(1,10))
In [8]: df
Out[8]:
Empty DataFrame
Columns: []
Index: [1, 2, 3, 4, 5, 6, 7, 8, 9]

Editar: incluso después de su enmienda con el .to_html, no puedo reproducir. Esta:

df = pd.DataFrame(columns=['A','B','C','D','E','F','G'])
df.to_html('test.html')

Produce:

<table border="1" class="dataframe">
  <thead>
    <tr style="text-align: right;">
      <th></th>
      <th>A</th>
      <th>B</th>
      <th>C</th>
      <th>D</th>
      <th>E</th>
      <th>F</th>
      <th>G</th>
    </tr>
  </thead>
  <tbody>
  </tbody>
</table>
Marcus V.
fuente
Edité la pregunta principal si eso ayuda. E: Editado de nuevo.
E. Muuli
9

¿Estás buscando algo así?

    COLUMN_NAMES=['A','B','C','D','E','F','G']
    df = pd.DataFrame(columns=COLUMN_NAMES)
    df.columns

   Index(['A', 'B', 'C', 'D', 'E', 'F', 'G'], dtype='object')
Linda
fuente
Además, no pierdo los nombres de mis columnas cuando lo intento. Está en formato de tabla html.
Linda
3

df.to_html() tiene un parámetro de columnas.

Simplemente pase las columnas al to_html()método.

df.to_html(columns=['A','B','C','D','E','F','G'])
Eric
fuente