diff --git a/src/go/core.py b/src/go/core.py --- a/src/go/core.py +++ b/src/go/core.py @@ -5,12 +5,20 @@ from .helperboard import HelperBoard from .gamerecord import GameRecord +PASS=(99,99) + + class Go: ## Initializes self.board to a list[r][c]=EMPTY. def __init__(self,boardSize=19): self.boardSize=boardSize self.board=[[EMPTY]*boardSize for x in range(boardSize)] self.toMove=BLACK + + # utility field to allow undoing moves. but only useful right after doMove. this class doesn't need it, so it is not kept correct at other times + self.captures=[None]*4 + self.captureCount=0 + self._helper=HelperBoard(self.board) self._freshHash=hashBoard(self.board) # always reflecting current state of the board self._hashes=[self._freshHash] @@ -24,15 +32,23 @@ class Go: # @return True on success, False on failure (illegal move) def doMove(self,color,r,c): if color!=self.toMove: log.warning("move by %s out of order",colorNames[color]) + if (r,c)==PASS: + self.toMove*=-1 # pass + self._hashes.append(self._freshHash) + return True if self.board[r][c]!=EMPTY: return False self.board[r][c]=color self._freshHash^=diffHash(r,c,EMPTY,color) # capture neighbors + self.captureCount=0 for dr,dc in ((-1,0),(1,0),(0,-1),(0,1)): self._helper.clear() - if not self._helper.floodFill(-color,r+dr,c+dc,EMPTY): self._remove() + if not self._helper.floodFill(-color,r+dr,c+dc,EMPTY): + self.captures[self.captureCount]=(r+dr,c+dc) + self.captureCount+=1 + self._remove() # check for suicide and prevent it self._helper.clear() @@ -46,15 +62,16 @@ class Go: return True def undoMove(self,r,c,captures): - assert self.board[r][c]==-1*self.toMove, "{0}!={1}".format(self.board[r][c],-1*self.toMove) + if (r,c)!=PASS: + assert self.board[r][c]==-1*self.toMove, "{0}!={1}".format(self.board[r][c],-1*self.toMove) - if len(captures)>0: - self._helper.clear() - for (ri,ci) in captures: - self._helper.floodFill(EMPTY,ri,ci) - self._fill(self.toMove) + if len(captures)>0: + self._helper.clear() + for (ri,ci) in captures: + self._helper.floodFill(EMPTY,ri,ci) + self._fill(self.toMove) - self.board[r][c]=EMPTY + self.board[r][c]=EMPTY self.toMove*=-1 self._hashes.pop() self._freshHash=self._hashes[-1]