123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147 |
- from graphics import *
- import time
- '''This program accepts a number n from the user, generates an nxn board,
- allows the user to place n queens, and checks to see if any of the queens
- can attack each other under the standard rules of chess: in other words,
- it determines if there is more than one queen in any given row, column, or
- diagonal. It then highlights any queens that are placed incorrectly. It uses a
- completely graphical interface - the command line need not be used.'''
- def smallcrown(point, win):
- '''draws a crown shape to represent a queen within a specified square
- on a board'''
- x = int(point.getX())
- y = int(point.getY())
- poly = Polygon(Point(x+.7, y+.3), Point(x+.3, y+.3), Point(x+.2, y+.6), Point(x+.35, y+.45), Point(x+.43, y+.6), Point(x+.5, y+.47), Point(x+.58, y+.6), Point(x+.65, y+.45), Point(x+.8, y+.6))
- poly.draw(win)
- def drawboard(win, n):
- '''draws a square grid of a specified size'''
- for i in range(n):
- line = Line(Point(i,0), Point(i, n))
- line.setWidth(1)
- line.draw(win)
- for i in range(n):
- line = Line(Point(0,i), Point(n,i))
- line.setWidth(1)
- line.draw(win)
- def placequeen(win, n):
- '''allows the user to place a specified number of 'queens' on a square
- board'''
- drawboard(win, n)
- pointX = []
- pointY = []
- for i in range(n):
- point = win.getMouse()
- pointX.append(int(point.getX()))
- pointY.append(int(point.getY()))
- smallcrown(point, win)
- return pointX, pointY
- def getMatrix(win, n):
- '''converts a board with n placed queens into a list of rows,
- with an empty space represented by 0 and a queen represented by 1'''
- X, Y = placequeen(win, n)
- Xrows = [[]]*n
- Yrows = [[]]*n
- for i in range(n):
- Xrows[i] = [0]*n
- Yrows[i] = [0]*n
- for i in range(n):
- Xrows[Y[i]][X[i]] = 1
- Yrows[X[i]][Y[i]] = 1
- return Xrows, Yrows
- def coord(n, x, y, qn):
- '''Takes row descriptions created by getMatrix and returns the following
- information for each queen: x, y, x+y, x-y'''
- coords = [[0,0]]*n
- coord = 0
- for row in range(n):
- for col in range(n):
- if x[row][col] == qn:
- coords[coord] = [row,col,row+col,row-col]
- coord += 1
- return coords
- def checkbit(n, coords, bp):
- '''uses a subset of the information generated by coord and uses it to
- check if there are multiple queens in any row, column, or diagonal. Makes
- a list of the (x,y) coordinates of those queens'''
- dct = {}
- lst = []
- for i in range(n):
- k = coords[i][bp]
- if dct.has_key(k):
- dct[k] = dct[k] + coords[i][0:2]
- else:
- dct[k] = coords[i][0:2]
- lst = dct.values()
- queens = []
- if len(lst) < n:
- for i in range(len(lst)):
- if len(lst[i]) <> 2:
- for b in range(0, len(lst[i]), 2):
- queens = queens + [lst[i][b:b+2]]
- return queens
- def checker(n, x, y, qn):
- '''Calls checkbit for each type of coordinate in turn'''
- coords = coord(n, x, y, qn)
- rows = checkbit(n, coords, 0)
- cols = checkbit(n, coords, 1)
- diag1 = checkbit(n, coords, 2)
- diag2 = checkbit(n, coords, 3)
- return rows, cols, diag1, diag2
- def main():
- '''This is the function to invoke to run the entire program'''
- win = GraphWin("Some Queens", 500, 500)
- f = Text(Point(250, 220), "Please enter a number for size of board")
- f.draw(win)
- e = Entry(Point(250, 250), 4)
- e.draw(win)
- b = Text(Point(250, 280), "Click to continue")
- b.draw(win)
- win.getMouse()
- n = int(e.getText())
- e.undraw()
- f.undraw()
- b.undraw()
- win.setCoords(0,0,n,n)
- x, y = getMatrix(win, n)
- rows, cols, diag1, diag2 = checker(n, x, y, 1)
- queens = rows + cols + diag1 + diag2
- time.sleep(0.5)
- if len(queens) == 0:
- t = Text(Point(n/2.0, (3*n)/4.0), "You're right!")
- t.setFill('blue')
- t.setSize(36)
- t.setStyle('bold')
- t.draw(win)
- else:
- for i in range(len(queens)):
- x = queens[i][0]
- y = queens[i][1]
- sqr = Rectangle(Point(y, x), Point(y+1, x+1))
- sqr.setFill('red')
- sqr.draw(win)
- smallcrown(Point(y, x), win)
- t = Text(Point(n/2.0, (3*n)/4.0), "Sorry, try again :(")
- t.setFill('blue')
- t.setSize(36)
- t.setStyle('bold')
- t.draw(win)
- clo = Text(Point(n/2.0, n/2.0), "Click to close")
- clo.setFill('blue')
- clo.setSize(20)
- clo.draw(win)
- win.getMouse()
- win.close()
- return
- main()
|