我使用 Python 类、random 和 Numpy 模块编写了一个扫雷游戏。通过选择难度,它会在 Numpy 的帮助下设置并创建棋盘的尺寸。然后,它也会根据选择的难度,全面随机设置地雷。
当您进行游戏时,特定功能会检查您选择踩踏的点周围的 8 个单元格,并返回那里存在的地雷数量。
经过一些修复后,我最后一次运行代码,希望它能正常工作......我得到的回报是在进行不同的比赛后,同一位置的不同值。
我检查了每个函数以及程序在每次运行时所采用的路径,但我仍然无法找到它在哪里犯了这个错误。
由于该网站的代码相当大,因此这里是 OnlineGDB 链接:
https://onlinegdb.com/JxHI-lRdP
快速预览:
def setupMines(self, mines: int = 15) -> None:
if len(self.board) <= 5: raise ValueError('Board too small')
self.mines = set()
while len(self.mines) < mines:
rand_row = randint(0, self.__dimension - 1)
rand_col = randint(0, self.__dimension - 1)
self.mines.add((rand_row, rand_col))
for row, col in self.mines:
self.board[row][col] = 1
def makePlay(self, row: int, col: int) -> None:
self.row = row - 1
self.column = col - 1
if self.board[row - 1][col - 1] == 1:
for i in 'You stepped on a mine!\nEnding program...':
print(i, end='')
wait(0.07)
exit(0)
elif self.board[row - 1][col - 1] == 0:
self.board[row - 1][col - 1] = -1
self.printBoard()
self.EndGame()
def checkPlay(self) -> int:
tip = 0
aux_row = -1
for _ in range(3):
aux_column = -1
for _ in range(3):
if (self.row + aux_row, self.column + aux_column) in self.mines: tip += 1
aux_column += 1
aux_row += 1
return tip
这是因为在 printBoard 方法中调用 checkPlay 方法的方式。 每次调用 checkPlay 时,它都会重新检查当前位置(self.row、self.column)周围的地雷,该位置可能会随着您进行新的游戏而改变。这会导致同一位置在不同的比赛后可能会给出不同的地雷数量。
确保每个单元格的地雷数量计算一次并存储; checkPlay 结果被正确存储和打印的位置:
import numpy as np
from random import randint
from time import sleep as wait
from sys import exit
class MineBoard:
def __init__(self) -> None:
self.dialogue()
def setupBoard(self, dimension: int = 9):
if not isinstance(dimension, int):
raise TypeError(f'Expected a type: int, instead got type:{type(dimension)}')
self.__dimension = dimension
self.board = np.zeros(shape=(dimension, dimension))
self.revealed_board = np.full((dimension, dimension), '-')
def setupMines(self, mines: int = 15) -> None:
if len(self.board) <= 5: raise ValueError('Board too small')
self.mines = set()
while len(self.mines) < mines:
rand_row = randint(0, self.__dimension - 1)
rand_col = randint(0, self.__dimension - 1)
self.mines.add((rand_row, rand_col))
for row, col in self.mines:
self.board[row][col] = 1
def makePlay(self, row: int, col: int) -> None:
self.row = row - 1
self.column = col - 1
if self.board[row - 1][col - 1] == 1:
for i in 'You stepped on a mine!\nEnding program...':
print(i, end='')
wait(0.07)
exit(0)
elif self.board[row - 1][col - 1] == 0:
self.revealed_board[row - 1][col - 1] = self.checkPlay()
self.printBoard()
self.EndGame()
def checkPlay(self) -> int:
tip = 0
for i in range(max(0, self.row - 1), min(self.__dimension, self.row + 2)):
for j in range(max(0, self.column - 1), min(self.__dimension, self.column + 2)):
if (i, j) in self.mines: tip += 1
return tip
def printBoard(self) -> str:
for i in range(self.__dimension):
print('\n')
for j in range(self.__dimension):
print(self.revealed_board[i][j], end='\t')
def EndGame(self) -> None:
scanner = list()
for i in self.board:
auxiliar = [x for x in i if x == -1]
scanner += auxiliar
if len(scanner) == 0:
for i in 'Congratulations, you beat the game!!':
print(i, end='')
wait(0.3)
exit(0)
else: return
def dialogue(self) -> None:
print('''\n\nMINESWEEPER\n\n''')
wait(1.0)
print('''Tip: Maximize the terminal.\n''')
wait(1.5)
choice = int(input('''CHOOSE YOUR DIFFICULTY:
(1) - Easy
(2) - Medium
(3) - Hard
--->> '''))
match choice:
case 1:
self.setupBoard()
self.setupMines()
case 2:
self.setupBoard(15)
self.setupMines(40)
case 3:
self.setupBoard(20)
self.setupMines(75)
while True:
print(f'\n\nMake your play! Choose a line and a column! {self.__dimension} by {self.__dimension}')
row = int(input('\nLine: '))
col = int(input('Column: '))
self.makePlay(row=row, col=col)
MineBoard()
添加 self.revealed_board 来存储棋盘的显示状态; makePlay 使用 checkPlay 的结果更新 self.revealed_board; checkPlay 计算一次指定单元格周围的地雷数量,printBoard 打印 self.revealed_board 中的值。
这可确保每个单元格的地雷计数计算并存储一次,从而防止不同玩法中同一位置的值不一致的问题。
玩得开心!