Python / Pandas-GUI pour afficher un DataFrame ou une matrice

J'utilise le paquet Pandas et il crée un objet DataFrame, qui est essentiellement une matrice étiquetée. Souvent, j'ai des colonnes qui ont de Longs Champs de chaîne, ou des dataframes avec beaucoup de colonnes, donc la commande d'impression simple ne fonctionne pas bien. J'ai écrit quelques fonctions de sortie de texte, mais elles ne sont pas géniales.

Ce que j'aimerais vraiment, c'est une interface graphique simple qui me permet d'interagir avec un dataframe / matrix / table. Tout comme vous le trouverez dans un outil SQL. Fondamentalement, une fenêtre qui a une lecture seule feuille de calcul comme vue dans les données. Je peux développer des colonnes, des pages de haut en bas à travers de longues tables,etc.

Je soupçonne que quelque chose comme ça existe, mais je dois googler avec les mauvais termes. Ce serait génial si c'est spécifique aux pandas, mais je suppose que je pourrais utiliser n'importe quel outil acceptant la matrice. (BTW-je suis sur Windows.)

Des pointeurs?

Ou, inversement, si quelqu'un connaît bien cet espace et sait que cela n'existe probablement pas, des suggestions sur s'il y a une interface graphique simple framework / widget que je pourrais utiliser pour rouler le mien? (Mais comme mes besoins sont limités, je suis réticent à devoir apprendre un grand framework GUI et faire un tas de codage pour cette pièce.)

46
demandé sur piRSquared 2012-05-17 16:48:00

16 réponses

J'utilise QTableWidget de PyQt pour afficher une DataFrame. Je crée un QTableWidgetObject et puis remplis avec QTableWidgetItems Créé avec des valeurs DataFrame. Voici l'extrait de code qui lit un fichier CSV, crée un DataFrame, puis s'affiche dans une interface graphique:

df  = read_csv(filename, index_col = 0,header = 0)
self.datatable = QtGui.QTableWidget(parent=self)
self.datatable.setColumnCount(len(df.columns))
self.datatable.setRowCount(len(df.index))
for i in range(len(df.index)):
    for j in range(len(df.columns)):
        self.datatable.setItem(i,j,QtGui.QTableWidgetItem(str(df.iget_value(i, j))))

Mise à Jour:

Comme cette réponse était assez ancienne, elle mérite une mise à jour. Il existe de nombreuses options disponibles maintenant pour afficher les dataframes dans L'interface graphique.

  1. comme d'autres l'ont souligné, Python IDEs tels que Spyder venez avec dataframe spectateur.
  2. qgrid est une autre option pour le widget notebook jupyter qui rend les dataframes dans le notebook.

Si quelqu'un veut toujours coder une interface graphique simple pour afficher les dataframes dans Jupyter, voici l'exemple complet et minimal utilisant Pyqt5 .

%gui qt5 
from PyQt5.QtWidgets import QWidget,QScrollArea, QTableWidget, QVBoxLayout,QTableWidgetItem
import pandas as pd

win = QWidget()
scroll = QScrollArea()
layout = QVBoxLayout()
table = QTableWidget()
scroll.setWidget(table)
layout.addWidget(table)
win.setLayout(layout)    


df = pd.DataFrame({"a" : [4 ,5, 6],"b" : [7, 8, 9],"c" : [10, 11, 12]},index = [1, 2, 3])
table.setColumnCount(len(df.columns))
table.setRowCount(len(df.index))
for i in range(len(df.index)):
    for j in range(len(df.columns)):
        table.setItem(i,j,QTableWidgetItem(str(df.iloc[i, j])))

win.show()

entrez la description de l'image ici

13
répondu user1319128 2018-08-07 05:32:45

Je n'étais pas entièrement satisfait d'autres interfaces graphiques, alors j'ai créé la mienne, que je maintiens maintenant sur Github. Exemple:

entrez la description de l'image ici

En dehors de la fonctionnalité de base table + plot, je voulais avoir un moyen spécifique de filtrer les données:

  • sélectionnez une colonne à filtrer dans une zone de liste déroulante
  • écrivez une "expression de soulignement" pour filtrer sur cette colonne en utilisant du code Python arbitraire. Par exemple: _ > 0 pour filtrer les valeurs positives uniquement, ou plus complexe des expressions comme (_ >= date(2016, 1, 1)) & (_ <= date(2016, 1, 31)) par exemple pour les colonnes datetime.
31
répondu bluenote10 2016-05-25 21:01:08

Pandas 0.13 fournit comme caractéristique expérimentale:

Support PySide pour les qtpandas DataFrameModel et DataFrameWidget

Voir https://github.com/pydata/pandas/blob/master/doc/source/faq.rst

Vous pouvez ajouter cette fonctionnalité en utilisant

from pandas.sandbox.qtpandas import DataFrameModel, DataFrameWidget
10
répondu working4coins 2014-03-04 08:07:48

La question était post en 2012 et d'autres réponses peuvent être trop anciennes pour postuler.

La réponse en 2016, nous devons utiliser Pycharm et il est livré avec DataFrame spectateur.

entrez la description de l'image ici

entrez la description de l'image ici

10
répondu guo 2016-11-04 02:10:50

Vous pouvez utiliser la méthode to_html () dataframe pour convertir le dataframe en html et l'afficher dans votre navigateur. Voici un exemple en supposant que vous avez un dataframe appelé df. Vous devriez vérifier la documentation pour voir quelles autres options sont disponibles dans la méthode to_html ().

# Format floating point numbers with 2 decimal places.
data_table = df.to_html(float_format=lambda x: '%6.2f' % x,
    classes="table display")
# The to_html() method forces a html table border of 1 pixel.
# I use 0  in my table so I  change the html, since there is no 
# border argument in the to_html() method.
data_table = data_table.replace('border="1"','border="0"')
# I alson like to display blanks instead on nan.
data_table = data_table.replace('nan', '')

Si vous voulez que la table soit bien formatée et défilante, vous pouvez utiliser le plug-in datatables pour jQuery www.datatables.net . Voici le javascript que j'utilise pour afficher une table défile dans les deux directions x et Y.

$('.table').dataTable({
    "bPaginate": true,
    "bLengthChange": true,
    "bSort": false,
    "bStateSave": true,
    "sScrollY": 900,
    "sScrollX": 1000,
    "aLengthMenu": [[50, 100, 250, 500, 1000, -1], [50, 100, 250, 500, 1000, "All"]],
    "iDisplayLength": 100,
});
8
répondu Yofe 2013-06-02 16:27:16

En plus de toutes les réponses précieuses, je voudrais mentionner que L'IDE Spyder ( https://github.com/spyder-ide ) a cette fonctionnalité comme vous pouvez le voir dans mon écran d'Impression ci-dessous:

entrez la description de l'image ici

C'est juste un fait objectif et non une publicité pour N'importe quel IDE :) Je ne veux pas déclencher de débat sur cette question.

6
répondu Adrien A. 2016-08-14 02:02:14

La meilleure solution que j'ai trouvée utilise qgrid (Voir ici, et également mentionné dans les documents pandas). Vous pouvez installer par

pip install qgrid

Et puis vous devez faire une autre installation (juste une fois) dans votre IPython notebook

qgrid.nbinstall()

Après, il est aussi facile que de prendre votre pandas df et en cours d'exécution

qgrid.show_grid(df)

L'autre bonne chose est qu'il rend dans nbviewer trop. Le voir en action ici

5
répondu cd98 2015-07-06 01:16:37

J'ai travaillé sur une interface graphique PyQt pour pandas DataFrame que vous pourriez trouver utile. Il comprend la copie, le filtrage et le tri.

Https://gist.github.com/jsexauer/f2bb0cc876828b54f2ed

2
répondu jsexauer 2015-01-11 14:41:28

Il semble qu'il n'y ait pas de solution facile. Donc, voici une petite fonction pour ouvrir un dataframe dans Excel. Ce n'est probablement pas un code de qualité de production, mais cela fonctionne pour moi!

def open_in_excel(df, index=True, excel_path="excel.exe", tmp_path='.'):
    """Open dataframe df in excel.

    excel_path - path to your copy of excel
    index=True - export the index of the dataframe as the first columns
    tmp_path    - directory to save the file in


    This creates a temporary file name, exports the dataframe to a csv of that file name,
    and then tells excel to open the file (in read only mode). (It uses df.to_csv instead
    of to_excel because if you don't have excel, you still get the csv.)

    Note - this does NOT delete the file when you exit. 
    """

    f=tempfile.NamedTemporaryFile(delete=False, dir=tmp_path, suffix='.csv', prefix='tmp_')
    tmp_name=f.name
    f.close()

    df.to_csv(tmp_name, index=index)
    cmd=[excel_path, '/r', '/e', tmp_name]
    try:
        ret_val=subprocess.Popen(cmd).pid
    except:
        print "open_in_excel(): failed to open excel"
        print "filename = ", tmp_name
        print "command line = ", cmd
        print "Unexpected error:", sys.exc_info()[0]

    return
1
répondu Ross R 2012-05-24 22:29:32

J'utilise des ordinateurs portables ipython pour conduire des pandas - les ordinateurs portables fournissent une bonne façon de construire et d'interagir de manière incrémentielle avec les structures de données pandas, y compris L'affichage HTML des dataframes: http://ipython.org/notebook.html

1
répondu stevegt 2013-06-01 17:18:04

Il y a tkintertable pour python2. 7 et pandastable pour python3.

1
répondu ostrokach 2014-11-06 21:49:29

Je vous recommande fortement d'utiliser QTableView pas QTableWidget. QTableView est basé sur la programmation de la vue Modèle.

Il y a 2 façons différentes comment ces widgets peuvent accéder à leurs données. La manière traditionnelle implique des widgets qui incluent des conteneurs internes pour stocker des données. Cette approche est très intuitive, cependant, dans de nombreuses applications non triviales, elle conduit à des problèmes de synchronisation des données. La deuxième approche est la programmation modèle/vue, dans laquelle les widgets ne pas maintenir les conteneurs de données internes

, j'ai écrit un modèle de pandas dataframe.

# -*- coding: utf-8 -*-
from PyQt5 import QtCore
from PyQt5 import QtWidgets
from PyQt5 import QtGui
import matplotlib.pyplot as plt

class PandasModel(QtCore.QAbstractTableModel):
    """
    Class to populate a table view with a pandas dataframe
    """

    def __init__(self, data, parent=None):
        QtCore.QAbstractTableModel.__init__(self, parent)
        self._data = data

    def rowCount(self, parent=None):
        return len(self._data.values)

    def columnCount(self, parent=None):
        return self._data.columns.size

    def data(self, index, role=QtCore.Qt.DisplayRole):
        if index.isValid():
            if role == QtCore.Qt.DisplayRole:
                if(index.column() != 0):
                    return str('%.2f'%self._data.values[index.row()][index.column()])
                else:
                    return str(self._data.values[index.row()][index.column()])
        return None

    def headerData(self, section, orientation, role):
        if orientation == QtCore.Qt.Horizontal and role == QtCore.Qt.DisplayRole:
            return self._data.columns[section]
        elif orientation == QtCore.Qt.Vertical and role == QtCore.Qt.DisplayRole:
            return str(self._data.index[section])
        return None

    def flags(self, index):
        flags = super(self.__class__,self).flags(index)
        flags |= QtCore.Qt.ItemIsSelectable
        flags |= QtCore.Qt.ItemIsEnabled
        return flags


if __name__=='__main__':
    import pandas as pd
    import numpy as np
    df = pd.DataFrame()
    df['Field1']=np.arange(0,10,.5)
    df['Field2']=np.arange(0,10,.5)
    app = QtWidgets.QApplication([])
    table = QtWidgets.QTableView()
    mymodel = PandasModel(df)
    table.setModel(mymodel)
    table.show()
    app.exec_()

Vous pouvez facilement modifier le modèle pour modifier ou afficher les éléments en fonction de vos besoins. Pour plus d'informations, reportez-vous à modelview

entrez la description de l'image ici

1
répondu Ali Mirzaei 2017-07-23 07:49:49

J'ai testé beaucoup de suggestions ici et aucune d'entre elles ne semble fonctionner ou s'installer facilement, en particulier pour Python 3, mais maintenant j'ai écrit une fonction qui accomplit essentiellement ce que je voulais. Besoin d'avoir ces dataframes en plein écran, et défilant parfois.

Donc, dans un environnement Linux utilisant Libreoffice Calc, inspiré par cette réponse {[7] } D'Unix et Linux StackExchange, voici ce que vous pouvez faire en Python 3:

import pandas as pd
import os

def viewDF(*dfs):
    filelist = ""
    for c, df in enumerate(dfs):    
        filename = 'tmp_df' + str(c) + '.csv'
        odsfile = 'tmp_df' + str(c) + '.ods'
        df.to_csv(filename)
        os.system("soffice --headless --convert-to ods  {}".format(filename))     
        filelist += odsfile + " "
    os.system("soffice --view {}".format(filelist)) 
    os.system("rm {}".format('tmp_df*'))

Utilisez-le comme ceci:

viewDF(df1, df2, df3)

J'ai appris quelque chose là-bas, qui est la syntaxe de substitution Python 3 {}".format les fichiers ouverts sont en lecture seule, en tout cas ce sont des fichiers qui sont supprimés plus tard, donc c'est effectivement une interface graphique pour les dataframes. Il va générer plusieurs instances de Libreoffice Calc pour chaque dataframe que vous lui donnez, que vous pouvez afficher en plein écran sur des écrans séparés, puis une fois que vous fermez Calc, il se nettoie après lui-même.

1
répondu cardamom 2017-10-14 17:50:52

La méthode to_clipboard() du dataframe peut être utilisée pour copier rapidement, puis coller le dataframe dans une feuille de calcul:

df.to_clipboard()
1
répondu Mike Bannister 2018-04-04 19:11:11

Je ne suis pas moi-même un utilisateur de Pandas, mais une recherche rapide pour "pandas gui" révèle la proposition du projet Pandas GSoC 2012 :

Actuellement, la seule façon d'interagir avec ces objets est via L'API. Ce projet propose d'ajouter une interface graphique Qt ou Tk simple pour visualiser et manipuler ces objets.

Donc, il n'y a pas D'interface graphique, mais si vous en écrivez une en utilisant Qt ou Tk, le projet pourrait être intéressé par votre code.

0
répondu Fred Foo 2012-05-17 12:55:30

Vous pouvez utiliser Github Atom avec le plugin Hydrogen. Dans Mac, vous pouvez utiliser les touches Cmd + Maj pour exécuter ligne par ligne. Même vous pouvez sélectionner uniquement la variable et voir à l'intérieur. Les DataFrames sont bien affichés et vous pouvez même copier. J'ai écrit un blog pour montrer la façon de configurer ces. http://ojitha.blogspot.com.au/2016/08/atom-as-spark-editor.html

0
répondu Ojitha 2017-02-23 10:14:42