Advertisement
Guest User

Untitled

a guest
Jul 22nd, 2017
486
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 23.83 KB | None | 0 0
  1. #!/usr/bin/env python3.2
  2. #
  3. # PrettyTable 0.5
  4. # Copyright (c) 2009, Luke Maurits <luke@maurits.id.au>
  5. # All rights reserved.
  6. # With contributions from:
  7. #  * Chris Clark
  8. #
  9. # Redistribution and use in source and binary forms, with or without
  10. # modification, are permitted provided that the following conditions are met:
  11. #
  12. # * Redistributions of source code must retain the above copyright notice,
  13. #   this list of conditions and the following disclaimer.
  14. # * Redistributions in binary form must reproduce the above copyright notice,
  15. #   this list of conditions and the following disclaimer in the documentation
  16. #   and/or other materials provided with the distribution.
  17. # * The name of the author may not be used to endorse or promote products
  18. #   derived from this software without specific prior written permission.
  19. #
  20. # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  21. # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  22. # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  23. # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
  24. # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
  25. # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
  26. # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
  27. # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
  28. # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  29. # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  30. # POSSIBILITY OF SUCH DAMAGE.
  31.  
  32. import cgi
  33. import copy
  34. import pickle
  35. import sys
  36.  
  37. FRAME = 0
  38. ALL   = 1
  39. NONE  = 2
  40.  
  41. class PrettyTable:
  42.  
  43.     def __init__(self, fields=None, caching=True, padding_width=1, left_padding=None, right_padding=None):
  44.  
  45.         """Return a new PrettyTable instance
  46.  
  47.        Arguments:
  48.  
  49.        fields - list or tuple of field names
  50.        caching - boolean value to turn string caching on/off
  51.        padding width - number of spaces between column lines and content"""
  52.  
  53.         # Data
  54.         self.fields = []
  55.         if fields:
  56.             self.set_field_names(fields)
  57.         else:
  58.             self.widths = []
  59.             self.aligns = []
  60.         self.set_padding_width(padding_width)
  61.         self.rows = []
  62.         self.cache = {}
  63.         self.html_cache = {}
  64.  
  65.         # Options
  66.         self.hrules = FRAME
  67.         self.caching = caching
  68.         self.padding_width = padding_width
  69.         self.left_padding = left_padding
  70.         self.right_padding = right_padding
  71.         self.vertical_char = "|"
  72.         self.horizontal_char = "-"
  73.         self.junction_char = "+"
  74.  
  75.     def __getslice__(self, i, j):
  76.  
  77.         """Return a new PrettyTable whose data rows are a slice of this one's
  78.  
  79.        Arguments:
  80.  
  81.        i - beginning slice index
  82.        j - ending slice index"""
  83.  
  84.         newtable = copy.deepcopy(self)
  85.         newtable.rows = self.rows[i:j]
  86.         return newtable
  87.  
  88.     def __str__(self):
  89.  
  90.         return self.get_string()
  91.  
  92.     ##############################
  93.     # ATTRIBUTE SETTERS          #
  94.     ##############################
  95.  
  96.     def set_field_names(self, fields):
  97.  
  98.         """Set the names of the fields
  99.  
  100.        Arguments:
  101.  
  102.        fields - list or tuple of field names"""
  103.  
  104.         # We *may* need to change the widths if this isn't the first time
  105.         # setting the field names.  This could certainly be done more
  106.         # efficiently.
  107.         if self.fields:
  108.             self.widths = [len(field) for field in fields]
  109.             for row in self.rows:
  110.                 for i in range(0,len(row)):
  111.                     if len(str(row[i])) > self.widths[i]:
  112.                         self.widths[i] = len(str(row[i]))
  113.         else:
  114.             self.widths = [len(field) for field in fields]
  115.         self.fields = fields
  116.         self.aligns = len(fields)*["c"]
  117.         self.cache = {}
  118.         self.html_cache = {}
  119.  
  120.     def set_field_align(self, fieldname, align):
  121.  
  122.         """Set the alignment of a field by its fieldname
  123.  
  124.        Arguments:
  125.  
  126.        fieldname - name of the field whose alignment is to be changed
  127.        align - desired alignment - "l" for left, "c" for centre and "r" for right"""
  128.  
  129.         if fieldname not in self.fields:
  130.             raise Exception("No field %s exists!" % fieldname)
  131.         if align not in ["l","c","r"]:
  132.             raise Exception("Alignment %s is invalid, use l, c or r!" % align)
  133.         self.aligns[self.fields.index(fieldname)] = align
  134.         self.cache = {}
  135.         self.html_cache = {}
  136.  
  137.     def set_padding_width(self, padding_width):
  138.  
  139.         """Set the number of empty spaces between a column's edge and its content
  140.  
  141.        Arguments:
  142.  
  143.        padding_width - number of spaces, must be a positive integer"""
  144.  
  145.         try:
  146.             assert int(padding_width) >= 0
  147.         except AssertionError:
  148.             raise Exception("Invalid value for padding_width: %s!" % str(padding_width))
  149.  
  150.         self.padding_width = padding_width
  151.         self.cache = {}
  152.         self.html_cache = {}
  153.  
  154.     def set_left_padding(self, left_padding):
  155.  
  156.         """Set the number of empty spaces between a column's left edge and its content
  157.  
  158.        Arguments:
  159.  
  160.        left_padding - number of spaces, must be a positive integer"""
  161.  
  162.         try:
  163.             assert left_padding == None or int(left_padding) >= 0
  164.         except AssertionError:
  165.             raise Exception("Invalid value for left_padding: %s!" % str(left_padding))
  166.  
  167.         self.left_padding = left_padding
  168.         self.cache = {}
  169.         self.html_cache = {}
  170.  
  171.     def set_right_padding(self, right_padding):
  172.  
  173.         """Set the number of empty spaces between a column's right edge and its content
  174.  
  175.        Arguments:
  176.  
  177.        right_padding - number of spaces, must be a positive integer"""
  178.  
  179.         try:
  180.             assert right_padding == None or int(right_padding) >= 0
  181.         except AssertionError:
  182.             raise Exception("Invalid value for right_padding: %s!" % str(right_padding))
  183.  
  184.         self.right_padding = right_padding
  185.         self.cache = {}
  186.         self.html_cache = {}
  187.  
  188.     def set_border_chars(self, vertical="|", horizontal="-", junction="+"):
  189.  
  190.         """Set the characters to use when drawing the table border
  191.  
  192.        Arguments:
  193.  
  194.        vertical - character used to draw a vertical line segment.  Default is |
  195.        horizontal - character used to draw a horizontal line segment.  Default is -
  196.        junction - character used to draw a line junction.  Default is +"""
  197.  
  198.         if len(vertical) > 1 or len(horizontal) > 1 or len(junction) > 1:
  199.             raise Exception("All border characters must be strings of length ONE!")
  200.         self.vertical_char = vertical
  201.         self.horizontal_char = horizontal
  202.         self.junction_char = junction
  203.         self.cache = {}
  204.  
  205.     ##############################
  206.     # DATA INPUT METHODS         #
  207.     ##############################
  208.  
  209.     def add_row(self, row):
  210.  
  211.         """Add a row to the table
  212.  
  213.        Arguments:
  214.  
  215.        row - row of data, should be a list with as many elements as the table
  216.        has fields"""
  217.  
  218.         if len(row) != len(self.fields):
  219.             raise Exception("Row has incorrect number of values, (actual) %d!=%d (expected)" %(len(row),len(self.fields)))
  220.         self.rows.append(row)
  221.         for i in range(0,len(row)):
  222.             if len(str(row[i])) > self.widths[i]:
  223.                 self.widths[i] = len(str(row[i]))
  224.         self.html_cache = {}
  225.  
  226.     def add_column(self, fieldname, column, align="c"):
  227.  
  228.         """Add a column to the table.
  229.  
  230.        Arguments:
  231.  
  232.        fieldname - name of the field to contain the new column of data
  233.        column - column of data, should be a list with as many elements as the
  234.        table has rows
  235.        align - desired alignment for this column - "l" for left, "c" for centre and "r" for right"""
  236.  
  237.         if len(self.rows) in (0, len(column)):
  238.             if align not in ["l","c","r"]:
  239.                 raise Exception("Alignment %s is invalid, use l, c or r!" % align)
  240.             self.fields.append(fieldname)
  241.             self.widths.append(len(fieldname))
  242.             self.aligns.append(align)
  243.             for i in range(0, len(column)):
  244.                 if len(self.rows) < i+1:
  245.                     self.rows.append([])
  246.                 self.rows[i].append(column[i])
  247.                 if len(str(column[i])) > self.widths[-1]:
  248.                     self.widths[-1] = len(str(column[i]))
  249.         else:
  250.             raise Exception("Column length %d does not match number of rows %d!" % (len(column), len(self.rows)))
  251.  
  252.     ##############################
  253.     # MISC PRIVATE METHODS       #
  254.     ##############################
  255.  
  256.     def _get_sorted_rows(self, start, end, sortby, reversesort):
  257.         # Sort rows using the "Decorate, Sort, Undecorate" (DSU) paradigm
  258.         rows = copy.deepcopy(self.rows[start:end])
  259.         sortindex = self.fields.index(sortby)
  260.         # Decorate
  261.         rows = [[row[sortindex]]+row for row in rows]
  262.         # Sort
  263.         rows.sort(reverse=reversesort)
  264.         # Undecorate
  265.         rows = [row[1:] for row in rows]
  266.         return rows
  267.  
  268.     def _get_paddings(self):
  269.  
  270.         if self.left_padding is not None:
  271.             lpad = self.left_padding
  272.         else:
  273.             lpad = self.padding_width
  274.         if self.right_padding is not None:
  275.             rpad = self.right_padding
  276.         else:
  277.             rpad = self.padding_width
  278.         return lpad, rpad
  279.  
  280.     ##############################
  281.     # ASCII PRINT/STRING METHODS #
  282.     ##############################
  283.  
  284.     def printt(self, start=0, end=None, fields=None, header=True, border=True, hrules=FRAME, sortby=None, reversesort=False):
  285.  
  286.         """Print table in current state to stdout.
  287.  
  288.        Arguments:
  289.  
  290.        start - index of first data row to include in output
  291.        end - index of last data row to include in output PLUS ONE (list slice style)
  292.        fields - names of fields (columns) to include
  293.        sortby - name of field to sort rows by
  294.        reversesort - True or False to sort in descending or ascending order
  295.        border - should be True or False to print or not print borders
  296.        hrules - controls printing of horizontal rules after each row.  Allowed values: FRAME, ALL, NONE"""
  297.  
  298.         print(self.get_string(start, end, fields, header, border, hrules, sortby, reversesort))
  299.  
  300.     def get_string(self, start=0, end=None, fields=None, header=True, border=True, hrules=FRAME, sortby=None, reversesort=False):
  301.  
  302.         """Return string representation of table in current state.
  303.  
  304.        Arguments:
  305.  
  306.        start - index of first data row to include in output
  307.        end - index of last data row to include in output PLUS ONE (list slice style)
  308.        fields - names of fields (columns) to include
  309.        sortby - name of field to sort rows by
  310.        reversesort - True or False to sort in descending or ascending order
  311.        border - should be True or False to print or not print borders
  312.        hrules - controls printing of horizontal rules after each row.  Allowed values: FRAME, ALL, NONE"""
  313.  
  314.         if self.caching:
  315.             key = pickle.dumps((start, end, fields, header, border, hrules, sortby, reversesort))
  316.             if key in self.cache:
  317.                 return self.cache[key]
  318.  
  319.         hrule = hrules or self.hrules
  320.         bits = []
  321.         if not self.fields:
  322.             return ""
  323.         if not header:
  324.             # Recalculate widths - avoids tables with long field names but narrow data looking odd
  325.             old_widths = self.widths[:]
  326.             self.widths = [0]*len(self.fields)
  327.             for row in self.rows:
  328.                 for i in range(0,len(row)):
  329.                     if len(str(row[i])) > self.widths[i]:
  330.                         self.widths[i] = len(str(row[i]))
  331.         if header:
  332.             bits.append(self._stringify_header(fields, border, hrules))
  333.         elif border and hrules != NONE:
  334.             bits.append(self._stringify_hrule(fields, border))
  335.         if sortby:
  336.             rows = self._get_sorted_rows(start, end, sortby, reversesort)
  337.         else:
  338.             rows = self.rows[start:end]
  339.         for row in rows:
  340.             bits.append(self._stringify_row(row, fields, border, hrule))
  341.         if border and not hrule:
  342.             bits.append(self._stringify_hrule(fields, border))
  343.         string = "\n".join(bits)
  344.  
  345.         if self.caching:
  346.             self.cache[key] = string
  347.  
  348.         if not header:
  349.             # Restore previous widths
  350.             self.widths = old_widths
  351.             for row in self.rows:
  352.                 for i in range(0,len(row)):
  353.                     if len(str(row[i])) > self.widths[i]:
  354.                         self.widths[i] = len(str(row[i]))
  355.  
  356.         return string
  357.  
  358.     def _stringify_hrule(self, fields=None, border=True):
  359.  
  360.         if not border:
  361.             return ""
  362.         lpad, rpad = self._get_paddings()
  363.         padding_width = lpad+rpad
  364.         bits = [self.junction_char]
  365.         for field, width in zip(self.fields, self.widths):
  366.             if fields and field not in fields:
  367.                 continue
  368.             bits.append((width+padding_width)*self.horizontal_char)
  369.             bits.append(self.junction_char)
  370.         return "".join(bits)
  371.  
  372.     def _stringify_header(self, fields=None, border=True, hrules=FRAME):
  373.  
  374.         lpad, rpad = self._get_paddings()
  375.         bits = []
  376.         if border:
  377.             if hrules != NONE:
  378.                 bits.append(self._stringify_hrule(fields, border))
  379.                 bits.append("\n")
  380.             bits.append(self.vertical_char)
  381.         for field, width in zip(self.fields, self.widths):
  382.             if fields and field not in fields:
  383.                 continue
  384.             bits.append(" " * lpad + field.center(width) + " " * rpad)
  385.             if border:
  386.                 bits.append(self.vertical_char)
  387.         if border and hrules != NONE:
  388.             bits.append("\n")
  389.             bits.append(self._stringify_hrule(fields, border))
  390.         return "".join(bits)
  391.  
  392.     def _stringify_row(self, row, fields=None, border=True, hrule=False):
  393.  
  394.         lpad, rpad = self._get_paddings()
  395.         bits = []
  396.         if border:
  397.             bits.append(self.vertical_char)
  398.         for field, value, width, align in zip(self.fields, row, self.widths, self.aligns):
  399.             if fields and field not in fields:
  400.                 continue
  401.             if align == "l":
  402.                 bits.append(" " * lpad + str(value).ljust(width) + " " * rpad)
  403.             elif align == "r":
  404.                 bits.append(" " * lpad + str(value).rjust(width) + " " * rpad)
  405.             else:
  406.                 bits.append(" " * lpad + str(value).center(width) + " " * rpad)
  407.             if border:
  408.                 bits.append(self.vertical_char)
  409.         if border and hrule == ALL:
  410.             bits.append("\n")
  411.             bits.append(self._stringify_hrule(fields, border))
  412.         return "".join(bits)
  413.  
  414.     ##############################
  415.     # HTML PRINT/STRING METHODS  #
  416.     ##############################
  417.  
  418.     def print_html(self, start=0, end=None, fields=None, sortby=None, reversesort=False, format=True, header=True, border=True, hrules=FRAME, attributes=None):
  419.  
  420.         """Print HTML formatted version of table in current state to stdout.
  421.  
  422.        Arguments:
  423.  
  424.        start - index of first data row to include in output
  425.        end - index of last data row to include in output PLUS ONE (list slice style)
  426.        fields - names of fields (columns) to include
  427.        sortby - name of field to sort rows by
  428.        format - should be True or False to attempt to format alignmet, padding, etc. or not
  429.        header - should be True or False to print a header showing field names or not
  430.        border - should be True or False to print or not print borders
  431.        hrules - include horizontal rule after each row
  432.        attributes - dictionary of name/value pairs to include as HTML attributes in the <table> tag"""
  433.  
  434.         print(self.get_html_string(start, end, fields, sortby, reversesort, format, header, border, hrules, attributes))
  435.  
  436.     def get_html_string(self, start=0, end=None, fields=None, sortby=None, reversesort=False, format=True, header=True, border=True, hrules=FRAME, attributes=None):
  437.  
  438.         """Return string representation of HTML formatted version of table in current state.
  439.  
  440.        Arguments:
  441.  
  442.        start - index of first data row to include in output
  443.        end - index of last data row to include in output PLUS ONE (list slice style)
  444.        fields - names of fields (columns) to include
  445.        sortby - name of
  446.        border - should be True or False to print or not print borders
  447.        format - should be True or False to attempt to format alignmet, padding, etc. or not
  448.        header - should be True or False to print a header showing field names or not
  449.        border - should be True or False to print or not print borders
  450.        hrules - include horizontal rule after each row
  451.        attributes - dictionary of name/value pairs to include as HTML attributes in the <table> tag"""
  452.  
  453.         if self.caching:
  454.             key = pickle.dumps((start, end, fields, format, header, border, hrules, sortby, reversesort, attributes))
  455.             if key in self.html_cache:
  456.                 return self.html_cache[key]
  457.  
  458.         if format:
  459.             tmp_html_func=self._get_formatted_html_string
  460.         else:
  461.             tmp_html_func=self._get_simple_html_string
  462.         string = tmp_html_func(start, end, fields, sortby, reversesort, header, border, hrules, attributes)
  463.  
  464.         if self.caching:
  465.             self.html_cache[key] = string
  466.  
  467.         return string
  468.  
  469.     def _get_simple_html_string(self, start, end, fields, sortby, reversesort, header, border, hrules, attributes):
  470.  
  471.         bits = []
  472.         # Slow but works
  473.         table_tag = '<table'
  474.         if border:
  475.             table_tag += ' border="1"'
  476.         if attributes:
  477.             for attr_name in attributes:
  478.                 table_tag += ' %s="%s"' % (attr_name, attributes[attr_name])
  479.         table_tag += '>'
  480.         bits.append(table_tag)
  481.         # Headers
  482.         bits.append("    <tr>")
  483.         for field in self.fields:
  484.             if fields and field not in fields:
  485.                 continue
  486.             bits.append("        <th>%s</th>" % cgi.escape(str(field)))
  487.         bits.append("    </tr>")
  488.         # Data
  489.         if sortby:
  490.             rows = self._get_sorted_rows(stard, end, sortby, reversesort)
  491.         else:
  492.             rows = self.rows
  493.         for row in self.rows:
  494.             bits.append("    <tr>")
  495.             for field, datum in zip(self.fields, row):
  496.                 if fields and field not in fields:
  497.                     continue
  498.                 bits.append("        <td>%s</td>" % cgi.escape(str(datum)))
  499.         bits.append("    </tr>")
  500.         bits.append("</table>")
  501.         string = "\n".join(bits)
  502.  
  503.         return string
  504.  
  505.     def _get_formatted_html_string(self, start, end, fields, sortby, reversesort, header, border, hrules, attributes):
  506.  
  507.         bits = []
  508.         # Slow but works
  509.         table_tag = '<table'
  510.         if border:
  511.             table_tag += ' border="1"'
  512.         if hrules == NONE:
  513.             table_tag += ' frame="vsides" rules="cols"'
  514.         if attributes:
  515.             for attr_name in attributes:
  516.                 table_tag += ' %s="%s"' % (attr_name, attributes[attr_name])
  517.         table_tag += '>'
  518.         bits.append(table_tag)
  519.         # Headers
  520.         lpad, rpad = self._get_paddings()
  521.         if header:
  522.             bits.append("    <tr>")
  523.             for field in self.fields:
  524.                 if fields and field not in fields:
  525.                     continue
  526.                 bits.append("        <th style=\"padding-left: %dem; padding-right: %dem; text-align: center\">%s</th>" % (lpad, rpad, cgi.escape(str(field))))
  527.             bits.append("    </tr>")
  528.         # Data
  529.         if sortby:
  530.             rows = self._get_sorted_rows(start, end, sortby, reversesort)
  531.         else:
  532.             rows = self.rows
  533.         for row in self.rows:
  534.             bits.append("    <tr>")
  535.             for field, align, datum in zip(self.fields, self.aligns, row):
  536.                 if fields and field not in fields:
  537.                     continue
  538.                 if align == "l":
  539.                     bits.append("        <td style=\"padding-left: %dem; padding-right: %dem; text-align: left\">%s</td>" % (lpad, rpad, cgi.escape(str(datum))))
  540.                 elif align == "r":
  541.                     bits.append("        <td style=\"padding-left: %dem; padding-right: %dem; text-align: right\">%s</td>" % (lpad, rpad, cgi.escape(str(datum))))
  542.                 else:
  543.                     bits.append("        <td style=\"padding-left: %dem; padding-right: %dem; text-align: center\">%s</td>" % (lpad, rpad, cgi.escape(str(datum))))
  544.         bits.append("    </tr>")
  545.         bits.append("</table>")
  546.         string = "\n".join(bits)
  547.  
  548.         return string
  549.  
  550. def main():
  551.  
  552.     x = PrettyTable(["City name", "Area", "Population", "Annual Rainfall"])
  553.     x.set_field_align("City name", "l") # Left align city names
  554.     x.add_row(["Adelaide",1295, 1158259, 600.5])
  555.     x.add_row(["Brisbane",5905, 1857594, 1146.4])
  556.     x.add_row(["Darwin", 112, 120900, 1714.7])
  557.     x.add_row(["Hobart", 1357, 205556, 619.5])
  558.     x.add_row(["Sydney", 2058, 4336374, 1214.8])
  559.     x.add_row(["Melbourne", 1566, 3806092, 646.9])
  560.     x.add_row(["Perth", 5386, 1554769, 869.4])
  561.     print(x)
  562.  
  563.     if len(sys.argv) > 1 and sys.argv[1] == "test":
  564.  
  565.     # This "test suite" is hideous and provides poor, arbitrary coverage.
  566.     # I'll replace it with some proper unit tests Sometime Soon (TM).
  567.     # Promise.
  568.         print("Testing field subset selection:")
  569.         x.printt(fields=["City name","Population"])
  570.         print("Testing row subset selection:")
  571.         x.printt(start=2, end=5)
  572.         print("Testing hrules settings:")
  573.         print("FRAME:")
  574.         x.printt(hrules=FRAME)
  575.         print("ALL:")
  576.         x.printt(hrules=ALL)
  577.         print("NONE:")
  578.         x.printt(hrules=NONE)
  579.         print("Testing lack of headers:")
  580.         x.printt(header=False)
  581.         x.printt(header=False, border=False)
  582.         print("Testing lack of borders:")
  583.         x.printt(border=False)
  584.         print("Testing sorting:")
  585.         x.printt(sortby="City name")
  586.         x.printt(sortby="Annual Rainfall")
  587.         x.printt(sortby="Annual Rainfall", reversesort=True)
  588.         print("Testing padding parameter:")
  589.         x.set_padding_width(0)
  590.         x.printt()
  591.         x.set_padding_width(5)
  592.         x.printt()
  593.         x.set_left_padding(5)
  594.         x.set_right_padding(0)
  595.         x.printt()
  596.         x.set_right_padding(20)
  597.         x.printt()
  598.         x.set_left_padding(None)
  599.         x.set_right_padding(None)
  600.         x.set_padding_width(2)
  601.         print("Testing changing characters")
  602.         x.set_border_chars("*","*","*")
  603.         x.printt()
  604.         x.set_border_chars("!","~","o")
  605.         x.printt()
  606.         x.set_border_chars("|","-","+")
  607.         print("Testing everything at once:")
  608.         x.printt(start=2, end=5, fields=["City name","Population"], border=False, hrules=True)
  609.         print("Rebuilding by columns:")
  610.         x = PrettyTable()
  611.         x.add_column("City name", ["Adelaide", "Brisbane", "Darwin", "Hobart", "Sydney", "Melbourne", "Perth"])
  612.         x.add_column("Area", [1295, 5905, 112, 1357, 2058, 1566, 5385])
  613.         x.add_column("Population", [1158259, 1857594, 120900, 205556, 4336374, 3806092, 1554769])
  614.         x.add_column("Annual Rainfall", [600.5, 1146.4, 1714.7, 619.5, 1214.8, 646.9, 869.4])
  615.         x.printt()
  616.         print("Testing HTML:")
  617.         x.print_html()
  618.         x.print_html(border=False)
  619.         x.print_html(border=True)
  620.         x.print_html(format=False)
  621.         x.print_html(attributes={"name": "table", "id": "table"})
  622.  
  623. if __name__ == "__main__":
  624.     main()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement