【问题标题】:How to print Sudoku grid more efficiently如何更有效地打印数独网格
【发布时间】:2021-05-07 21:32:06
【问题描述】:

我正在终端中编程数独游戏,我想将网格打印到控制台,并在其周围有一个正方形,如下图所示。 我的代码没有问题,只是效率低。

我想让它更高效、更简短(使用列表推导、字符串乘法等)。 董事会是这样定义的, board = [[_ for _ in range(9)] for _ in range(9)]

这就是我正在使用的功能:

def Print_Board(board):

    print("\n-------------------------")

    for i in range(9):
        for j in range(9):
            if board[i][j] is not None:
                if j == 0:
                    print("|", end=" ")
                print(f"{board[i][j]} ", end="")
            if (j + 1) % 3 == 0:
                print("|", end=" ")
        if (i + 1) % 3 == 0:
            print("\n-------------------------", end=" ")
        print()

【问题讨论】:

  • 除非您要打印数千次,否则优化不会显着提高性能。
  • 如果您实际使用它的值,请不要使用_ 作为变量名。
  • 我认为 sys.stdout 比普通打印要快,尽管差异不会很明显,除非你打印出非常大量的数独,我猜你不会。我同意尼特亚。
  • 根据经验,尽量减少print()s 的数量。理想情况下,构建游戏字段的完整字符串表示并立即打印。此外,由于您的实际数字会有所不同,因此所问的问题是无用的。你必须先考虑一下什么数据结构保存了游戏字段,然后再问如何打印。

标签: python python-3.x list-comprehension


【解决方案1】:

您可以构建一个板格式并将所有数据扔给它:

bar = '-------------------------\n'
lnf = '|' +(' {:}'*3 + ' |')*3 + '\n'
bft = bar + (lnf*3+bar)*3
print(bft.format(*(el for rw in board for el in rw)))

当然,您只需要构建一次格式。之后就是打印了。



来自 cmets 中 JonSG 的建议将其封装在一个闭包中:

def make_board_printer():
    bar = '-------------------------\n'
    lnf = '|' +(' {:}'*3 + ' |')*3 + '\n'
    bft = bar + (lnf*3+bar)*3
    return (lambda bd:print(bft.format(*(el for rw in bd for el in rw))))

是一个返回板打印机函数的函数:

# make a printer:
b_print = make_board_printer()

# then as needed
b_print(board)

【讨论】:

  • 如果我真的在打高尔夫球,那么酒吧也将是一个乘法:-)。
  • 您应该添加一个扩展答案,该答案使用闭包来构造模板并返回一个 lambda 以使用它进行打印。
  • 天哪,我非常喜欢这个答案。不仅它简短而甜美,而且在概念上也很棒。创建一个可以重复使用的打印模板将 IO 从格式化函数中取出,同样重要的是,只调用一次 print()。干得好。
【解决方案2】:

你可以这样做:

def print_board(board):
    print("\n-------------------------")
    for row_num, row in enumerate(board):
        print("|", end=" ")
        for col_num, item in enumerate(row):
            print(item, end=" ")
            if (col_num + 1) % 3 == 0:
                print("|", end=" ")
        if (row_num + 1) % 3 == 0:
            print("\n-------------------------", end=" ")
        print()


if __name__ == '__main__':
    print_board(board=[range(9) for _ in range(9)])

【讨论】:

    【解决方案3】:

    这里是您的问题的(不是更易读的)解决方案:

    board = [range(1,10) for i in range(9)]
    print("-"*25)
    for idx, row in enumerate(board):
        rowStr = " | ".join([" ".join(map(str, row[i:i+3])) for i in range(0, len(row), 3)])
        print(f'| {rowStr} |')
        if (idx+1) % 3 == 0:
            print("-"*25)
    

    输出:

    -------------------------
    | 1 2 3 | 4 5 6 | 7 8 9 |
    | 1 2 3 | 4 5 6 | 7 8 9 |
    | 1 2 3 | 4 5 6 | 7 8 9 |
    -------------------------
    | 1 2 3 | 4 5 6 | 7 8 9 |
    | 1 2 3 | 4 5 6 | 7 8 9 |
    | 1 2 3 | 4 5 6 | 7 8 9 |
    -------------------------
    | 1 2 3 | 4 5 6 | 7 8 9 |
    | 1 2 3 | 4 5 6 | 7 8 9 |
    | 1 2 3 | 4 5 6 | 7 8 9 |
    -------------------------
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-05-10
      • 2021-05-14
      • 1970-01-01
      • 2021-05-15
      • 1970-01-01
      • 1970-01-01
      • 2017-08-23
      • 1970-01-01
      相关资源
      最近更新 更多