-
Notifications
You must be signed in to change notification settings - Fork 0
/
AlphaBeta.py
114 lines (91 loc) · 2.59 KB
/
AlphaBeta.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
from time import time
from GameBoard import dictBoard
import math
from Position import Pos
DEPTH_LIMIT = 2
def board_value(board):
"""
:param board:
:type board: dictBoard
:return:
:rtype:
"""
if board.isTerminal():
return board.utility()
dragonCount = 0
guardCount = 0
for i in board.board.values():
if i == 'D':
dragonCount += 1
elif i == 'G':
guardCount += 1
if board.king_clear:
kclear = 50
else:
kclear = -50
return ((5-dragonCount)*(100)) + ((3-guardCount)*-100) \
+ (6-board.king_pos.x)*20 + board.get_neighbours_guards(board.king_pos)*20 \
+ kclear + board.num_little_ds()*100
def minMaxFunction(state):
"""
:param state: Current GameBoard
:type state: GameBoard.dictBoard
:return: utility of move, original position, move position
:rtype: (int, (Position.Pos, Position.Pos))
"""
if state.isTerminal():
return state.utility(), None
move_list = []
alpha = -math.inf
beta = math.inf
for s in state.successors():
move_list.append((minValue(s[0], alpha, beta), s[1]))
move = max(move_list, key=lambda x: x[0])
return move[1]
def maxValue(state, alpha, beta, depth=0):
"""
:param state:
:type state: GameBoard.dictBoard
:return:
"""
if state.isTerminal():
return state.utility()
if depth == DEPTH_LIMIT:
return board_value(state)
value = -math.inf
for (boardState, (location, move)) in state.successors():
value = minValue(boardState, alpha, beta, depth + 1)
if value >= beta:
return alpha
alpha = max(alpha, value)
return alpha
def minValue(state, alpha, beta, depth=0):
"""
:param state:
:type state: GameBoard.dictBoard
:return:
"""
if state.isTerminal():
return state.utility()
if depth == DEPTH_LIMIT:
return board_value(state)
value = math.inf
for (boardState, (location, move)) in state.successors():
value = maxValue(boardState, alpha, beta, depth+1)
if value <= alpha:
return beta
beta = min(beta, value)
return beta
b = dictBoard(None)
total_time = time()
for i in range(0,100):
t_start = time()
x, y = minMaxFunction(b)
move1 = b.this_one(x, y)[0]
print("move",i+1)
print(move1)
b = move1
print(time() - t_start)
print("cumulative time:", time() - total_time)
# print(move4)
# TODO the scoer varies as the king close to the end of the board and if a drangon is on the way instead of a clear path