Python无库实现SQLite3游戏数据库表格带表头对齐打印
实现SQLite查询结果的对齐式表格打印(无第三方库)
问题场景
我为自制游戏写了一段Python代码,用来从SQLite3数据库读取玩家的得分数据:
def read_all_tables(self): self.cursor.execute('SELECT Name, Gender, Age, Score, Date, Time FROM Link JOIN Scores ON Score_ID = Scores.ID JOIN Player ON Player_ID = Player.id ORDER BY Score DESC') Data = self.cursor.fetchall() for Row in Data: print() for record in range(len(Row)): print(Row[record], end=" ")
但现在输出的格式完全没有章法,看起来乱糟糟的:
HAMMAD MALE 18 900 07/01/18 13:07:02
HAMMAD MALE 18 850 07/01/18 13:30:11
INDERVEER MALE 18 750 07/01/18 13:35:46
HAMMAD MALE 18 500 07/01/18 13:08:29
...(剩余行省略)
想请教下,不用任何第三方库的前提下,怎么输出带表头的整齐对齐的表格?
解决方案
刚好处理过类似的需求,核心思路就是先算出每一列需要的最大宽度,然后用字符串格式化把每列内容统一对齐到这个宽度,再加上表头和分隔线,就能得到规整的表格了。
修改后的完整代码如下:
def read_all_tables(self): # 执行查询,同时准备获取表头 self.cursor.execute('SELECT Name, Gender, Age, Score, Date, Time FROM Link JOIN Scores ON Score_ID = Scores.ID JOIN Player ON Player_ID = Player.id ORDER BY Score DESC') # 从游标描述中提取表头字段名 headers = [col[0] for col in self.cursor.description] # 获取所有查询数据 data_rows = self.cursor.fetchall() # 计算每一列的最大显示宽度:表头长度和该列所有数据的字符串长度取最大值 column_widths = [] for col_idx in range(len(headers)): # 初始宽度设为表头的长度 max_width = len(headers[col_idx]) # 遍历所有数据行,更新该列的最大宽度 for row in data_rows: # 把数值类型转成字符串再计算长度 current_length = len(str(row[col_idx])) if current_length > max_width: max_width = current_length column_widths.append(max_width) # 打印表头行 header_output = "" for header, width in zip(headers, column_widths): # 左对齐,填充到指定宽度,后面加分隔符 header_output += f"{header:<{width}} | " # 去掉末尾多余的" | "后打印 print(header_output.rstrip(" | ")) # 打印表头和数据之间的分隔线 separator = "" for width in column_widths: separator += "-" * width + " + " print(separator.rstrip(" + ")) # 逐行打印数据 for row in data_rows: row_output = "" for value, width in zip(row, column_widths): row_output += f"{str(value):<{width}} | " print(row_output.rstrip(" | "))
代码细节说明
- 获取表头:通过
cursor.description可以拿到查询结果的字段元数据,我们提取其中的字段名作为表格的表头,不用手动写死,适配性更强。 - 计算列宽:对每一列,我们对比表头的长度和该列所有数据的字符串长度,取最大值作为这一列的显示宽度,这样不管内容长短都能对齐。
- 格式化输出:用Python的f-string做格式化,
{content:<{width}}表示左对齐并填充到指定宽度,表头、分隔线、数据行都用统一的规则输出,最后去掉每行末尾多余的分隔符,让表格更干净。
运行后的输出会变成这样:
Name | Gender | Age | Score | Date | Time -----------+--------+-----+-------+----------+---------- HAMMAD | MALE | 18 | 900 | 07/01/18 | 13:07:02 HAMMAD | MALE | 18 | 850 | 07/01/18 | 13:30:11 INDERVEER | MALE | 18 | 750 | 07/01/18 | 13:35:46 HAMMAD | MALE | 18 | 500 | 07/01/18 | 13:08:29 ...
内容的提问来源于stack exchange,提问作者user9156598
相关产品推荐
相关产品推荐

