diff --git a/dlx.py b/dlx.py --- a/dlx.py +++ b/dlx.py @@ -14,7 +14,7 @@ class Cell: class Column(Cell): def __init__(self,name,*args,**kwargs): - super().__init__(*args,**kwargs) + super().__init__(*args,up=self,down=self,**kwargs) self.name=name self.size=0 @@ -45,10 +45,11 @@ class Column(Cell): self.left.right=self -class Header: - def __init__(self,left=None,right=None): - self.left=left - self.right=right +class Header(Column): + def __init__(self): + super().__init__("head") + self.left=self + self.right=self self._res=[] def search(self,k=0): diff --git a/pieces.py b/pieces.py --- a/pieces.py +++ b/pieces.py @@ -72,19 +72,3 @@ def fits(board,piece,shift): if board[coords]: return False res.append(coords) return res - - -if __name__=="__main__": - board=np.zeros((1,2,3)) - boat=np.array([[[0,1,0],[1,1,1]]]) - es=np.array([[[1,1,0],[0,1,1]]]) - el=np.array([[[1,1,1],[1,0,0]]]) - - pieces={"boat":boat} - - for (name,piece) in pieces.items(): - for p in listRotations(piece): - for shift in listShifts(board,p): - fit=fits(board,p,shift) - if fit is not False: - print(fit) diff --git a/tetris.py b/tetris.py --- a/tetris.py +++ b/tetris.py @@ -1,122 +1,56 @@ -EMPTY="." -FULL="O" - +import numpy as np -class Piece: - def __init__(self,variants): - self.variants=variants +from pieces import listRotations,listShifts,fits +from dlx import Header,Column,Cell -pieceSet=dict() - -pieceSet["sq"]=Piece([ - # OO - # OO - ((0,0),(0,1),(1,0),(1,1)) -]) +board=np.zeros((1,4,3)) +boat=np.array([[[0,1,0],[1,1,1]]]) +sz=np.array([[[1,1,0],[0,1,1]]]) +el=np.array([[[1,1,1],[1,0,0]]]) -pieceSet["long"]=Piece([ - # OOOO - ((0,0),(0,1),(0,2),(0,3)), - ((0,0),(1,0),(2,0),(3,0)) -]) - -pieceSet["boat"]=Piece([ - # OOO - # .O. - ((0,0),(0,1),(0,2),(1,1)), - ((0,0),(1,0),(2,0),(1,1)), - ((0,0),(1,-1),(1,0),(1,1)), - ((0,0),(1,-1),(1,0),(2,0)) -]) +(nz,ny,nx)=board.shape +pieces=[("el1",el),("el2",el),("sz",sz)] +header=[name for (name,p) in pieces]+\ + [(z,y,x) for z in range(nz) for y in range(ny) for x in range(nx) if not board[z][y][x]] +index={label:i for (i,label) in enumerate(header)} -pieceSet["sz"]=Piece([ - # .OO - # OO. - ((0,0),(0,1),(1,-1),(1,0)), - ((0,0),(1,0),(1,1),(2,1)), - - # OO. - # .OO - ((0,0),(0,1),(1,1),(1,2)), - ((0,0),(1,0),(1,-1),(2,-1)) -]) +matrix=[] -pieceSet["el"]=Piece([ - # OOO - # O.. - ((0,0),(1,0),(0,1),(0,2)), - ((0,0),(1,0),(2,0),(2,1)), - ((0,0),(1,-2),(1,-1),(1,0)), - ((0,0),(0,1),(1,1),(2,1)), - - # OOO - # ..O - ((0,0),(0,1),(0,2),(1,2)), - ((0,0),(0,1),(1,0),(2,0)), - ((0,0),(1,0),(1,1),(1,2)), - ((0,0),(1,0),(2,0),(2,-1)) -]) - -WIDTH=8 -HEIGHT=5 -board=[[EMPTY]*WIDTH for r in range(HEIGHT)] - +for (name,piece) in pieces: + for p in listRotations(piece): + for shift in listShifts(board,p): + fit=fits(board,p,shift) + if fit is not False: + row=[0]*len(header) + row[index[name]]=1 + for coords in fit: row[index[coords]]=1 + matrix.append(row) -def fill(board,pieces): - point=firstEmpty(board) - if not point: return True - res=[] - for (i,(k,p)) in enumerate(pieces): - if k==0: continue - for v in p.variants: - if place(board,point,v): - pieces[i][0]-=1 - partialRes=fill(board,pieces) - if partialRes: - res.append(((point,v), partialRes)) - remove(board,point,v) - pieces[i][0]+=1 - return res +# print(header) +# for row in matrix: print(row) - -def firstEmpty(board): - for (r,row) in enumerate(board): - for (c,cell) in enumerate(row): - if cell==EMPTY: - return (r,c) - return None - +columns=[] +head=Header() +for label in header: + c=Column(label) + head.left.right=c + c.left=head.left + head.left=c + c.right=head + columns.append(c) -def place(board,point,piece): - (r,c)=point - if not all(0<=r+ri