Hübsch Drucken eines Pandas-Datenrahmens

112

Wie kann ich einen Pandas-Datenrahmen als schöne textbasierte Tabelle wie folgt drucken?

+------------+---------+-------------+
| column_one | col_two |   column_3  |
+------------+---------+-------------+
|          0 |  0.0001 | ABCD        |
|          1 |  1e-005 | ABCD        |
|          2 |  1e-006 | long string |
|          3 |  1e-007 | ABCD        |
+------------+---------+-------------+
Ofer
quelle

Antworten:

179

Ich habe gerade ein großartiges Tool für diesen Bedarf gefunden, es heißt tabulate .

Es druckt tabellarische Daten und arbeitet mit DataFrame.

from tabulate import tabulate
import pandas as pd

df = pd.DataFrame({'col_two' : [0.0001, 1e-005 , 1e-006, 1e-007],
                   'column_3' : ['ABCD', 'ABCD', 'long string', 'ABCD']})
print(tabulate(df, headers='keys', tablefmt='psql'))

+----+-----------+-------------+
|    |   col_two | column_3    |
|----+-----------+-------------|
|  0 |    0.0001 | ABCD        |
|  1 |    1e-05  | ABCD        |
|  2 |    1e-06  | long string |
|  3 |    1e-07  | ABCD        |
+----+-----------+-------------+

Hinweis:

Um Zeilenindizes für alle Datentypen zu unterdrücken, übergeben Sie showindex="never"oder showindex=False.

Romain
quelle
5
Wenn Sie keinen Zugang zur Blutungskante haben, können Sie tabulate([list(row) for row in df.values], headers=list(df.columns))den Index loswerden
Pedro M Duarte
1
Funktioniert nicht sehr gut, wenn Sie Hierarchien in Zeilenindex und Spalten haben.
Siddharth
Stellen Sie sicher, dass Sie dies tun print(tabulate(df, **kwargs))und nicht einfach tabulate(df, **kwargs); Letzteres zeigt alle neuen Zeilen \n....
Dror
6
Um die linke showindex=False
Arthur
23

Ein einfacher Ansatz ist die Ausgabe als HTML, was Pandas sofort tut :

df.to_html('temp.html')
ErichBSchulz
quelle
16

Pandas> = 1,0

Wenn Sie möchten, dass eine eingebaute Funktion Ihre Daten in einem Github-Markdown speichert, haben Sie jetzt eine. Schauen Sie sich an to_markdown:

df = pd.DataFrame({"A": [1, 2, 3], "B": [1, 2, 3]}, index=['a', 'a', 'b'])  
print(df.to_markdown()) 

|    |   A |   B |
|:---|----:|----:|
| a  |   1 |   1 |
| a  |   2 |   2 |
| b  |   3 |   3 |

So sieht das auf Github aus:

Geben Sie hier die Bildbeschreibung ein

Beachten Sie, dass das tabulatePaket weiterhin installiert sein muss.

cs95
quelle
15

Sie können Stettytable verwenden , um die Tabelle als Text zu rendern. Der Trick besteht darin, den data_frame in eine speicherinterne CSV-Datei zu konvertieren und von Stettytable lesen zu lassen. Hier ist der Code:

from StringIO import StringIO
import prettytable    

output = StringIO()
data_frame.to_csv(output)
output.seek(0)
pt = prettytable.from_csv(output)
print pt
Ofer
quelle
Welche Version von Pandas war das?
WAF
4
AFAIK prettytablewird größtenteils als Abbruchware angesehen. Schade auch, denn es war ein schönes Paket. :(
dmn
@dmn also wird es nicht mehr gepflegt?
Myon
prettytablehat seit dem 6. April 2013 keine Veröffentlichung mehr. tabulateist sein spiritueller Vorgänger und hat regelmäßige Veröffentlichungen, die letzte am 24. Januar 2019.
noddy
15

Wenn Sie sich in einem Jupyter-Notizbuch befinden, können Sie den folgenden Code ausführen, um den Datenrahmen interaktiv in einer gut formatierten Tabelle anzuzeigen.

Diese Antwort baut auf der obigen Antwort to_html ('temp.html') auf, aber anstatt eine Datei zu erstellen, wird die gut formatierte Tabelle direkt im Notizbuch angezeigt:

from IPython.display import display, HTML

display(HTML(df.to_html()))

Gutschrift für diesen Code aufgrund eines Beispiels unter: DataFrame als Tabelle in iPython Notebook anzeigen

Mark Andersen
quelle
7

Ich habe Ofers Antwort eine Weile benutzt und fand sie in den meisten Fällen großartig. Leider aufgrund von Inkonsistenzen zwischen to_csv und hübschtable von pandas ich prettytable eine andere Methode verwenden.

Ein Fehlerfall ist ein Datenrahmen mit Kommas:

pd.DataFrame({'A': [1, 2], 'B': ['a,', 'b']})

Prettytable löst einen Fehler in der Form aus:

Error: Could not determine delimiter

Die folgende Funktion behandelt diesen Fall:

def format_for_print(df):    
    table = PrettyTable([''] + list(df.columns))
    for row in df.itertuples():
        table.add_row(row)
    return str(table)

Wenn Sie sich nicht für den Index interessieren, verwenden Sie:

def format_for_print2(df):    
    table = PrettyTable(list(df.columns))
    for row in df.itertuples():
        table.add_row(row[1:])
    return str(table)
ejrb
quelle
Hallo, die format_for_print()Funktion scheint nicht den Index des Pandas DataFrame zu drucken. Ich habe den Index mit festgelegt, df.index.name = 'index'aber dadurch wird die Indexspalte nicht mit einem Namen gedruckt.
Edesz
2

Im Anschluss an Mark Antwort, wenn Sie nicht Jupyter aus irgendeinem Grund, zB Sie einige schnelle Tests auf der Konsole machen wollen, können Sie das verwenden DataFrame.to_stringMethode, die aus arbeitet - zumindest - Pandas 0,12 (2014) weiter .

import pandas as pd

matrix = [(1, 23, 45), (789, 1, 23), (45, 678, 90)]
df = pd.DataFrame(matrix, columns=list('abc'))
print(df.to_string())

#  outputs:
#       a    b   c
#  0    1   23  45
#  1  789    1  23
#  2   45  678  90
Sigint
quelle
0

Vielleicht suchen Sie so etwas:

def tableize(df):
    if not isinstance(df, pd.DataFrame):
        return
    df_columns = df.columns.tolist() 
    max_len_in_lst = lambda lst: len(sorted(lst, reverse=True, key=len)[0])
    align_center = lambda st, sz: "{0}{1}{0}".format(" "*(1+(sz-len(st))//2), st)[:sz] if len(st) < sz else st
    align_right = lambda st, sz: "{0}{1} ".format(" "*(sz-len(st)-1), st) if len(st) < sz else st
    max_col_len = max_len_in_lst(df_columns)
    max_val_len_for_col = dict([(col, max_len_in_lst(df.iloc[:,idx].astype('str'))) for idx, col in enumerate(df_columns)])
    col_sizes = dict([(col, 2 + max(max_val_len_for_col.get(col, 0), max_col_len)) for col in df_columns])
    build_hline = lambda row: '+'.join(['-' * col_sizes[col] for col in row]).join(['+', '+'])
    build_data = lambda row, align: "|".join([align(str(val), col_sizes[df_columns[idx]]) for idx, val in enumerate(row)]).join(['|', '|'])
    hline = build_hline(df_columns)
    out = [hline, build_data(df_columns, align_center), hline]
    for _, row in df.iterrows():
        out.append(build_data(row.tolist(), align_right))
    out.append(hline)
    return "\n".join(out)


df = pd.DataFrame([[1, 2, 3], [11111, 22, 333]], columns=['a', 'b', 'c'])
print tableize(df)
Ausgabe:
+ ------- + ---- + ----- +
| a | b | c |
+ ------- + ---- + ----- +
| 1 | 2 | 3 |
| 11111 | 22 | 333 |
+ ------- + ---- + ----- +
Pafkone
quelle
-5

Ich wollte einen Papierausdruck eines Datenrahmens, aber ich wollte auch einige Ergebnisse und Kommentare auf derselben Seite hinzufügen. Ich habe das oben Genannte durchgearbeitet und konnte nicht bekommen, was ich wollte. Am Ende habe ich die Anweisungen file.write (df1.to_csv ()) und file.write (",,, blah ,,,,,, blah") verwendet, um meine Extras auf die Seite zu bringen. Als ich die CSV-Datei öffnete, ging es direkt zu einer Tabelle, in der alles im richtigen Tempo und Format gedruckt wurde.

jon
quelle