Python-确定Tic Tac Toe Winn

2024-04-24 13:35:40 发布

您现在位置:Python中文网/ 问答频道 /正文

我试图写一个代码,以确定赢家的井字游戏。(这是大学作业)

为此,我编写了以下函数:

This code only checks for horizontal lines, I haven't added the rest. I feel that this is something that needs a bit of hardcoding.

def iswinner(board, decorator):
    win = True
    for row in range(len(board)):
        for col in range(len(board)):
            if board[row][col] == decorator:
                win = True
            else:
                win = False
                break

其中“board”是大小为n^2的二维数组,“decorator”是“X”或“O”值

我希望完成的是,函数循环遍历2D数组的行。然后循环遍历每行中的值。如果该元素与“decorator”匹配,则它将继续并检查下一个元素,如果不匹配,则它将从第一个循环中断并转到下一行。直到在同一行中找到n个元素。然后它会给出一个bool值True或者False。

代码似乎没有做到这一点,甚至当我用下面的“board”检查时,它给了我一个“True”的输出

check_list = [['O', 'X', 'X'],
              ['O', 'X', 'O'],
              ['O', 'X', 'X']]

非常感谢!

最好的, 塞义德


Tags: 函数代码inboardfalsetrue元素for
3条回答

这样做的一个方法是创建一个集合(生成器函数会更好)来检查所有可能的索引组合是否获胜。然后循环遍历这些索引组合,检查它们是否都包含相同的值,如果是,那么就是一个胜利。

def win_indexes(n):
    # Rows
    for r in range(n):
        yield [(r, c) for c in range(n)]
    # Columns
    for c in range(n):
        yield [(r, c) for r in range(n)]
    # Diagonal top left to bottom right
    yield [(i, i) for i in range(n)]
    # Diagonal top right to bottom left
    yield [(i, n - 1 - i) for i in range(n)


def is_winner(board, decorator):
    n = len(board)
    for indexes in win_indexes(n):
        if all(board[r][c] == decorator for r, c in indexes):
            return True
    return False

您可以通过创建一个generatorlines()来完成此操作,它生成所有8行(3行、3列和2条对角线),然后检查是否有任何行仅由一个元素组成,并且该元素不是None

一旦你有了

board = [
    [ 'o', 'x', None], 
    [None, 'x', None], 
    [None, 'x',  'o']
]

执行以下操作:

def _lines(board):
    yield from board  # the rows
    yield [board[i][i] for i in range(len(board))]  # one of the diagonals

def lines(board):
    yield from _lines(board)
    # rotate the board 90 degrees to get the columns and the other diagonal
    yield from _lines(list(zip(*reversed(board))))

def who_won(board):
    for line in lines(board):
        if len(set(line)) == 1 and line[0] is not None:
            return line[0]
    return None  # if we got this far, there's no winner

对于我上面给出的那块板,list(lines(board))将返回

[['o', 'x', None], 
 [None, 'x', None], 
 [None, 'x', 'o'], 
 ['o', 'x', 'o'], 
 (None, None, 'o'), 
 ('x', 'x', 'x'), 
 ('o', None, None), 
 [None, 'x', None]]

其中3个元素是元组而不是列表,因为^{}返回元组。您可以使用列表理解来转换它们,请参见this question了解如何进行转换,以及zip(*reversed(some_list))所做操作的更多详细信息。

然后只需要检查每个元素,看看它是否只有一个惟一的元素,方法是转换成一个^{}和那个惟一的元素is not None

这项工程未经修改的任何大小的tic tac趾板,而不仅仅是3×3。

您只需为每一行创建一个集合,并检查其长度。如果它只包含一个元素,那么游戏就赢了。

def returnWinner(board):
    for row in board:
        if len(set(row)) == 1:
            return row[0]
    return -1

如果有一行“O”,则返回“O”;如果有一行“X”,则返回“X”;否则返回-1。

下面是一个完整的Tic-Tac-Toe检查器的代码,应该不难理解,但不要犹豫问:

import numpy as np

def checkRows(board):
    for row in board:
        if len(set(row)) == 1:
            return row[0]
    return 0

def checkDiagonals(board):
    if len(set([board[i][i] for i in range(len(board))])) == 1:
        return board[0][0]
    if len(set([board[i][len(board)-i-1] for i in range(len(board))])) == 1:
        return board[0][len(board)-1]
    return 0

def checkWin(board):
    #transposition to check rows, then columns
    for newBoard in [board, np.transpose(board)]:
        result = checkRows(newBoard)
        if result:
            return result
    return checkDiagonals(board)


a = [['X', 'A', 'X'],
     ['A', 'X', 'A'],
     ['A', 'X', 'A']]

print(checkWin(a))

请注意,无论您选择在tic tac toe(“O”&;“X”和“bloop”&;“!”中放置什么符号,它都可以工作,对于任何大小的网格,只要它是正方形。

相关问题 更多 >