-
Notifications
You must be signed in to change notification settings - Fork 1
/
board.py
executable file
·249 lines (210 loc) · 8.46 KB
/
board.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
import os
import math
from copy import deepcopy
from utility import *
RED = '\033[1;31;40m'
RED_BG = '\033[0;31;47m'
BLUE_BG = '\033[0;34;47m'
YELLOW = '\033[1;33;40m'
BLUE = '\033[1;34;40m'
MAGENTA = '\033[1;35;40m'
CYAN = '\033[1;36;40m'
WHITE = '\033[1;37;40m'
#make an empty board
def initializeBoard():
Board = []
for i in range(BOARD_HEIGHT):
Board.append([])
for j in range(BOARD_WIDTH):
Board[i].append(' ')
return Board
#check if the column is filled or not
def isColumnValid(Board, Col):
if Board[0][Col] == ' ':
return True
return False
#check the search range for rows and columns
def isRangeValid(row, col):
if row >= 0 and col >= 0 and row < BOARD_HEIGHT and col < BOARD_WIDTH:
return True
return False
#return all valid moves (empty columns) from the board
def getValidMoves(Board):
Columns = []
for Col in range(BOARD_WIDTH):
if isColumnValid(Board, Col):
Columns.append(Col)
return Columns
#places the current move's player ['x'|'o'] in the referenced column in the board
def makeMove(board, col, player):
#deepcopy is used to take acopy of current board and not affecting the original one
tempBoard = deepcopy(board)
for row in range(5,-1,-1):
if tempBoard[row][col] == ' ':
tempBoard[row][col] = player
return tempBoard, row, col
#check if the played move is in empty column or not
def isValidMove(col, board):
for row in range(BOARD_HEIGHT):
if board[row][col] == ' ':
return True
return False
#check if the board is filled with players' moves
def isBoardFilled(board):
#Check the first row and Selected colmun if it filled or not
for row in range(BOARD_HEIGHT):
for col in range(BOARD_WIDTH):
if board[row][col]==' ': return False
return True
#find four or more of ('x'|'o') in arow in any direction
def findFours(board):
#find four or more of ('x'|'o') in arow in vertical direction
def verticalCheck(row, col):
fourInARow = False
count = 0
for rowIndex in range(row, BOARD_HEIGHT):
if board[rowIndex][col] == board[row][col]:
count += 1
else:
break
if count >= 4:
fourInARow = True
return fourInARow, count
#find four or more of ('x'|'o') in arow in horizontal direction
def horizontalCheck(row, col):
fourInARow = False
count = 0
for colIndex in range(col, BOARD_WIDTH):
if board[row][colIndex] == board[row][col]:
count += 1
else:
break
if count >= 4:
fourInARow = True
return fourInARow, count
#find four or more of ('x'|'o') in arow in postive diagonal direction
def posDiagonalCheck(row,col):
# check for diagonals with positive slope
slope = None
count = 0
colIndex = col
for rowIndex in range(row, BOARD_HEIGHT):
if colIndex > BOARD_HEIGHT:
break
elif board[rowIndex][colIndex] == board[row][col]:
count += 1
else:
break
colIndex += 1 # increment column when row is incremented
if count >= 4:
slope = 'positive'
return slope, count
#find four or more of ('x'|'o') in arow in negative diagonal direction
def negDiagonalCheck(row, col):
# check for diagonals with positive slope
slope = None
count = 0
colIndex = col
for rowIndex in range(row, -1, -1):
if colIndex > 6:
break
elif board[rowIndex][colIndex] == board[row][col]:
count += 1
else:
break
colIndex += 1 # increment column when row is decremented
if count >= 4:
slope = 'negative'
return slope, count
#find four or more of ('x'|'o') in arow in any diagonal direction
def diagonalCheck(row,col):
positiveSlop , positiveCount = posDiagonalCheck(row,col)
negativeSlop , negativeCount = negDiagonalCheck(row,col)
if positiveSlop == 'positive' and negativeSlop == 'negative':
fourInARow = True
slope = 'both'
elif positiveSlop == None and negativeSlop == 'negative':
fourInARow = True
slope = 'negative'
elif positiveSlop == 'positive' and negativeSlop == None:
fourInARow = True
slope = 'positive'
else:
fourInARow = False
slope = None
return fourInARow, slope, positiveCount, negativeCount
#make the winning moves in uppercase
def capitalizeFourInARow(row, col, dir):
if dir == 'vertical':
for rowIndex in range(verticalCount):
board[row+rowIndex][col] = board[row+rowIndex][col].upper()
elif dir == 'horizontal':
for colIndex in range(horizontalCount):
board[row][col+colIndex] = board[row][col+colIndex].upper()
elif dir == 'diagonal':
if slope == 'positive' or slope == 'both':
for diagIndex in range(positiveCount):
board[row+diagIndex][col+diagIndex] = board[row+diagIndex][col+diagIndex].upper()
elif slope == 'negative' or slope == 'both':
for diagIndex in range(negativeCount):
board[row-diagIndex][col+diagIndex] = board[row-diagIndex][col+diagIndex].upper()
#initialize the variables
FourInRowFlag = False
slope = None
verticalCount = 0
horizontalCount = 0
positiveCount = 0
negativeCount = 0
for rowIndex in range(BOARD_HEIGHT):
for colIndex in range(BOARD_WIDTH):
if board[rowIndex][colIndex] != ' ':
# check for a vertical match starts at (rowIndex, colIndex)
fourInARow, verticalCount = verticalCheck(rowIndex, colIndex)
if fourInARow:
capitalizeFourInARow(rowIndex, colIndex, 'vertical')
FourInRowFlag = True
fourInARow, horizontalCount = horizontalCheck(rowIndex, colIndex)
# check for horizontal match starts at (rowIndex, colIndex)
if fourInARow:
capitalizeFourInARow(rowIndex, colIndex, 'horizontal')
FourInRowFlag = True
# check for diagonal match starts at (rowIndex, colIndex)
# also, get the slope of the four if there is one
fourInARow, slope , positiveCount, negativeCount = diagonalCheck(rowIndex, colIndex)
if fourInARow:
capitalizeFourInARow(rowIndex, colIndex, 'diagonal')
FourInRowFlag = True
return FourInRowFlag
#gets number of the empty valid locations in the board
def getEmptyLocations(board):
emptyLocations = 0
for row in range(BOARD_HEIGHT):
for col in range(BOARD_WIDTH):
if board[row][col] == ' ':
emptyLocations += 1
return emptyLocations
def printBoard(Board):
#clear console/terminal screen
os.system('cls' if os.name == 'nt' else 'clear')
emptyLocations = 42 - getEmptyLocations(Board) #get empty locations
print('')
print(YELLOW + ' ROUND #' + str(emptyLocations) + WHITE, end=" ") #print round number
print('')
print('')
print("\t 1 2 3 4 5 6 7 ")
print("\t - - - - - - - ")
for i in range(0, BOARD_HEIGHT, 1):
print(WHITE+"\t",i+1,' ',end="")
for j in range(BOARD_WIDTH):
if str(Board[i][j]) == 'x':
print("| " + BLUE + str(Board[i][j]) +WHITE, end=" ") #print colored 'x'
elif str(Board[i][j]) == 'o':
print("| " + RED + str(Board[i][j]) +WHITE, end=" ") #print colored 'o'
elif str(Board[i][j]) == 'X':
print("| " + BLUE_BG + str(Board[i][j]) +WHITE, end=" ") #print colored 'X'
elif str(Board[i][j]) == 'O':
print("| " + RED_BG + str(Board[i][j]) +WHITE, end=" ") #print colored 'O'
else:
print("| " + str(Board[i][j]), end=" ")
print("|")
print('')