我试图实现一个简单的TicTacToe游戏,但我无法制作某个列表的浅层副本。 这是我脚本的最小摘录,它提出了我的问题:
SIZE = 3 # size of game board
PLAYERS = (PLAYER, COMPUTER) = "X", "O"
class TicTacToe(list):
""" Class handling game board """
def __init__(self, size=SIZE, players=PLAYERS):
""" Board size defaults to 3 """
super().__init__([[" " for idx in range(size)] for jdx in range(size)])
self._size = size
def winner_move(self, letter, range_):
""" Determine winner move - range_ members are tuples """
for tile in range_:
sim = self[:] # shallow copy of game board for simulation
sim[tile[0]][tile[1]] = letter
print("Current board:")
print(self)
# code makes some decisions here and continues
def get_empty(self):
""" Return empty places on board as a set of (row, col) """
return {(row, col) for row in range(self._size)\
for col in range(self._size) if self[row][col] == " "}
board = TicTacToe()
board.winner_move(PLAYER, board.get_empty())
虽然我只为sim分配新值,但更改反映在" main"板。我也试过
sim = list(self)
和
sim = [item for item in self]
但两者都给出了相同的结果。
有什么建议我做错了吗?
答案 0 :(得分:1)
Arpegius' comment是对的。你有一个嵌套列表。使用sim = self[:]
,sim = list(self)
或sim = [item for item in self]
,您将获得一个新的外部列表,但它将是内部列表的相同引用列表。
sim = [lst[:] for lst in self]
或
sim = [list(lst) for lst in self]
会有效,但
from copy import deepcopy
# ...
sim = deepcopy(self)
更优雅,其目的更容易理解。请参阅its documentation。