代码之家  ›  专栏  ›  技术社区  ›  Cleb

如何将熊猫数据框显示为datatable?

  •  12
  • Cleb  · 技术社区  · 7 年前

    我想以 DataTable . 在下面的简化示例中,我读取了用户提供的两个数字,它们决定了表的行数和列数。然后,此表的元素数将正确显示,但该表不会显示。

    我认为,问题是我把桌子传错了。当我尝试时

    return jsonify(number_elements=a * b,
                       my_table=df)
    

    我得到了错误

    anaconda2/lib/python2.7/json/encoder。py”,默认情况下,第184行 raise TypeError(repr(o)+“不可JSON序列化”)

    类型错误:0 1 2 3 0 51 35 10 84 1 30 60 79 24不是JSON 可序列化

    如果我使用

    return jsonify(number_elements=a * b,
                       my_table=df.to_json())
    

    然后没有错误,但仍不显示表格。

    如何正确执行此操作?

    我的 index.html 文件如下所示:

    <!DOCTYPE html>
    <html lang="en">
      <head>
        <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
        <link href="https://netdna.bootstrapcdn.com/bootstrap/3.0.0/css/bootstrap.min.css"
              rel="stylesheet">
         <link href="https://cdn.datatables.net/1.10.16/css/jquery.dataTables.min.css"
               rel="stylesheet">
      <script type=text/javascript>
        $(function() {
          $('a#calculate').bind('click', function() {
            $.getJSON('/_get_table', {
              a: $('input[name="a"]').val(),
              b: $('input[name="b"]').val()
            }, function(data) {
              $("#elements").text(data.number_elements);
              $("#a_nice_table").DataTable(data.my_table);
            });
            return false;
          });
        });
      </script>
      </head>
      <body>
        <div class="container">
          <div class="header">
            <h3 class="text-muted">Create a pretty table</h3>
          </div>
    
          <div>
            <p>Number of rows</p>
            <input type="text" size="5" name="a" value="2">
            <p>Number of columns</p>
            <input type="text" size="5" name="b" value="4">
    
            <p><a href="javascript:void();" id="calculate">get a pretty table</a></p>
             <p>Result</p>
            <p>Number of elements:</p>
              <span id="elements">Hallo</span><br>
              <span id="a_nice_table">Here should be a table</span>
          </div>
        </div>
      </body>
    </html>
    

    和我的文件 app.py 如下所示:

    from flask import Flask, render_template, request, jsonify
    import pandas as pd
    import numpy as np
    
    # Initialize the Flask application
    app = Flask(__name__)
    
    
    @app.route('/')
    def index():
        return render_template('index.html')
    
    
    @app.route('/_get_table')
    def get_table():
        a = request.args.get('a', type=int)
        b = request.args.get('b', type=int)
    
        df = pd.DataFrame(np.random.randint(0, 100, size=(a, b)))
    
        return jsonify(number_elements=a * b,
                       my_table=df)
    
    
    if __name__ == '__main__':
        app.run(debug=True)
    
    2 回复  |  直到 7 年前
        1
  •  15
  •   Scratch'N'Purr    7 年前

    这是我的实现。我做了一些优化,比如将js文件移到HTML的末尾:

    指数html

    <!DOCTYPE html>
    <html lang="en">
      <head>
        <link href="https://netdna.bootstrapcdn.com/bootstrap/3.0.0/css/bootstrap.min.css" rel="stylesheet">
        <link href="https://cdn.datatables.net/1.10.16/css/jquery.dataTables.min.css" rel="stylesheet">
      </head>
      <body>
        <div class="container">
          <div class="header">
            <h3 class="text-muted">Create a pretty table</h3>
          </div>
    
          <div>
            <p>Number of rows</p>
            <input type="text" size="5" name="a" value="2">
            <p>Number of columns</p>
            <input type="text" size="5" name="b" value="4">
    
            <p><a href="javascript:void();" id="calculate">get a pretty table</a></p>
             <p>Result</p>
            <p>Number of elements:</p>
              <span id="elements">Hallo</span><br>
              <table id="a_nice_table">Here should be a table</table>
          </div>
        </div>
        <script src="https://code.jquery.com/jquery-1.12.4.js" type="text/javascript"></script>
        <script src="https://cdn.datatables.net/1.10.16/js/jquery.dataTables.min.js" type="text/javascript"></script>
        <script type="text/javascript">
          $(document).ready(function() {
            var table = null;
            $('a#calculate').bind('click', function() {
              $.getJSON('/_get_table', {
                a: $('input[name="a"]').val(),
                b: $('input[name="b"]').val()
              }, function(data) {
                $("#elements").text(data.number_elements);
                if (table !== null) {
                  table.destroy();
                  table = null;
                  $("#a_nice_table").empty();
                }
                table = $("#a_nice_table").DataTable({
                  data: data.my_table,
                  columns: data.columns
                });
              });
              return false;
            });
          });
        </script>
      </body>
    </html>
    

    应用程序。py公司

    from flask import Flask, render_template, request, jsonify
    import pandas as pd
    import numpy as np
    import json
    
    # Initialize the Flask application
    app = Flask(__name__)
    
    
    @app.route('/')
    def index():
        return render_template('index.html')
    
    
    @app.route('/_get_table')
    def get_table():
        a = request.args.get('a', type=int)
        b = request.args.get('b', type=int)
    
        df = pd.DataFrame(np.random.randint(0, 100, size=(a, b)))
    
        return jsonify(number_elements=a * b,
                       my_table=json.loads(df.to_json(orient="split"))["data"],
                       columns=[{"title": str(col)} for col in json.loads(df.to_json(orient="split"))["columns"]])
    
    
    if __name__ == '__main__':
        app.run(debug=True)
    

    我修改的内容:

    1. 添加了js文件以呈现DataTable。
    2. 将js文件向下移动到HTML的底部。
    3. 在js中添加了一个检查,以在使用新数据刷新数据时销毁和清除列。
    4. 使用 to_json 方向为的方法 split 为DataTables生成json数据。
    5. 还必须添加 columns 要使用的DataTables的json字符串,在使用 to\u json

    下面是如何使用熊猫的 to_html 要生成表,请执行以下操作:

    指数html

    <!DOCTYPE html>
    <html lang="en">
      <head>
        <link href="https://netdna.bootstrapcdn.com/bootstrap/3.0.0/css/bootstrap.min.css" rel="stylesheet">
        <link href="https://cdn.datatables.net/1.10.16/css/jquery.dataTables.min.css" rel="stylesheet">
      </head>
      <body>
        <div class="container">
          <div class="header">
            <h3 class="text-muted">Create a pretty table</h3>
          </div>
    
          <div>
            <p>Number of rows</p>
            <input type="text" size="5" name="a" value="2">
            <p>Number of columns</p>
            <input type="text" size="5" name="b" value="4">
    
            <p><a href="javascript:void();" id="calculate">get a pretty table</a></p>
             <p>Result</p>
            <p>Number of elements:</p>
              <span id="elements">Hallo</span><br>
              <div id="mytablediv">Here should be a table</div>
          </div>
        </div>
        <script src="https://code.jquery.com/jquery-1.12.4.js" type="text/javascript"></script>
        <script src="https://cdn.datatables.net/1.10.16/js/jquery.dataTables.min.js" type="text/javascript"></script>
        <script type="text/javascript">
          $(document).ready(function() {
            var table = null;
            $('a#calculate').bind('click', function() {
              $.getJSON('/_get_table', {
                a: $('input[name="a"]').val(),
                b: $('input[name="b"]').val()
              }, function(data) {
                $("#elements").text(data.number_elements);
                if (table !== null) {
                  table.destroy();
                  table = null;
                  $("#a_nice_table").empty();
                }
                $("#mytablediv").html(data.my_table);
                table = $("#a_nice_table").DataTable();
              });
              return false;
            });
          });
        </script>
      </body>
    </html>
    

    应用程序。py公司

    from flask import Flask, render_template, request, jsonify
    import pandas as pd
    import numpy as np
    
    # Initialize the Flask application
    app = Flask(__name__)
    
    
    @app.route('/')
    def index():
        return render_template('index2.html')
    
    
    @app.route('/_get_table')
    def get_table():
        a = request.args.get('a', type=int)
        b = request.args.get('b', type=int)
    
        df = pd.DataFrame(np.random.randint(0, 100, size=(a, b)))
    
        return jsonify(number_elements=a * b,
                       my_table=df.to_html(classes='table table-striped" id = "a_nice_table',
                                           index=False, border=0))
    
    
    if __name__ == '__main__':
        app.run(debug=True)
    

    与以前实施的区别:

    1. 在HTML中,我必须添加一个父div以保存生成的HTML表。在这种情况下,我称之为 mytablediv .
    2. 在JS端的HTML中,我必须基本上修改 mytablediv 在我生成数据之后。此HTML内容来自 to\u html 输出
    3. 在JS端的HTML中,我不必再向 DataTable 函数,因为这将由HTML代码处理。
    4. 在里面 app.py ,我不得不使用hackey方法为pandas生成一个HTML ID标记。ID标记让JS知道要修改哪个元素。我使用了来自 here .
    5. 在里面 应用程序。py公司 ,因为我现在正在生成HTML,所以还必须显式指定其他表样式选项,如 border=0 index=False 模仿以前的实现。
        2
  •  1
  •   arnaud    7 年前

    你不应该生成一个 html 第一张桌子?利用 pandas.DataFrame.to_html() 作用事实上 documentation of DataTables 显示使用html表的示例。