Added a python sample agent
[progcomp2012.git] / samples / asmodeus / asmodeus.py
1 #!/usr/bin/python -u
2
3 #NOTE: The -u option is required for unbuffered stdin/stdout.
4 #       If stdin/stdout are buffered, the manager program will not recieve any messages and assume that the agent has timed out.
5
6 '''
7  asmodeus.py - A sample Stratego AI for the UCC Programming Competition 2012
8
9  Written in python, the slithery language 
10
11  author Sam Moore (matches) [SZM]
12  website http://matches.ucc.asn.au/stratego
13  email progcomp@ucc.asn.au or matches@ucc.asn.au
14  git git.ucc.asn.au/progcomp2012.git
15 '''
16
17 import sys
18 import random
19
20 ranks = ('B','1','2','3','4','5','6','7','8','9','s','F', '?', '+')
21
22 def move(x, y, direction):
23         if direction == "UP":
24                 return (x,y-1)
25         elif direction == "DOWN":
26                 return (x,y+1)
27         elif direction == "LEFT":
28                 return (x-1, y)
29         elif direction == "RIGHT":
30                 return (x+1, y)
31         print "Error in move!"
32         return (x,y)
33
34 def oppositeColour(colour):
35         if colour == "RED":
36                 return "BLUE"
37         elif colour == "BLUE":
38                 return "RED"
39         else:
40                 return "NONE"
41
42 class Piece:
43         def __init__(self, colour, rank, x, y):
44                 self.colour = colour
45                 self.rank = rank
46                 self.x = x
47                 self.y = y
48         
49
50
51
52 class Asmodeus:
53         def __init__(self):
54                 #sys.stderr.write("Asmodeus __init__ here...\n");
55                 self.turn = 0
56                 self.board = []
57                 self.units = []
58                 if self.Setup():
59                         while self.MakeMove():
60                                 pass
61                 
62
63         def Setup(self):
64                 #sys.stderr.write("Asmodeus Setup here...\n");
65                 setup = sys.stdin.readline().split(' ')
66                 self.colour = setup[0]
67                 self.opponentName = setup[1]
68                 self.width = int(setup[2])
69                 self.height = int(setup[3])
70                 for x in range(0, self.width):
71                         self.board.append([])
72                         for y in range(0, self.height):         
73                                 self.board[x].append(None)
74                 if self.colour == "RED":
75                         print "FB8sB479B8\nBB31555583\n6724898974\n967B669999"
76                 elif self.colour == "BLUE":
77                         print "967B669999\n6724898974\nBB31555583\nFB8sB479B8"
78                 return True
79
80         def MoveCycle(self):
81                 #sys.stderr.write("Asmodeus MakeMove here...\n");
82                 if self.InterpretResult() == False or self.ReadBoard() == False or self.MakeMove() == False:
83                         return False
84                 self.turn += 1
85                 return self.InterpretResult()
86
87         def MakeMove(self):
88                 #TODO: Over-ride this function in base classes with more complex move behaviour
89
90                 #sys.stderr.write("Asmodeus MakeRandomMove here...\n")
91                 #self.debugPrintBoard()
92                 while True:
93                         if len(self.units) <= 0:
94                                 return False
95                         piece = random.choice(self.units)
96                         if piece == None:
97                                 continue
98                         if piece.rank == '?' or piece.rank == 'B' or piece.rank == 'F':
99                                 continue
100
101                         direction = random.choice(("UP", "DOWN", "LEFT", "RIGHT"))
102                         p = move(piece.x, piece.y, direction)
103                         if p[0] >= 0 and p[0] < self.width and p[1] >= 0 and p[1] < self.height:
104                                 if self.board[p[0]][p[1]] == None or self.board[p[0]][p[1]].colour == oppositeColour(self.colour):
105                                         print str(piece.x) + " " + str(piece.y) + " " + direction
106                                         break
107                 return True
108                                                         
109                         
110         def ReadBoard(self):
111                 #sys.stderr.write("Asmodeus ReadBoard here...\n");
112                 for y in range(0,self.height):
113                         row = sys.stdin.readline()
114                         for x in range(0,len(row)-1):
115                                 if self.turn == 0:
116                                         if row[x] == '.':
117                                                 pass
118                                         elif row[x] == '#':
119                                                 self.board[x][y] = Piece(oppositeColour(self.colour), '?',x,y)
120                                         elif row[x] == '+':
121                                                 self.board[x][y] = Piece("NONE", '+', x, y)
122                                         else:
123                                                 self.board[x][y] = Piece(self.colour, row[x],x,y)
124                                                 self.units.append(self.board[x][y])
125                                 else:
126                                         pass
127                 return True
128                 
129
130         def InterpretResult(self):
131                 #sys.stderr.write("Asmodeus InterpretResult here...\n")
132                 result = sys.stdin.readline().split(' ')
133                 #sys.stderr.write("     Read status line \"" + str(result) + "\"\n")
134                 if self.turn == 0:
135                         return True
136
137                 x = int(result[0].strip())
138                 y = int(result[1].strip())
139
140
141                 #sys.stderr.write("     Board position " + str(x) + " " + str(y) + " is OK!\n")         
142
143                 direction = result[2].strip()
144                 outcome = result[3].strip()
145                 
146                 p = move(x,y,direction)
147
148                 if outcome == "OK":
149                         self.board[p[0]][p[1]] = self.board[x][y]
150                         self.board[x][y].x = p[0]
151                         self.board[x][y].y = p[1]
152
153                         self.board[x][y] = None
154                 elif outcome == "KILLS":
155                         if self.board[p[0]][p[1]] == None:
156                                 return False
157
158                         if self.board[p[0]][p[1]].colour == self.colour:
159                                 self.units.remove(self.board[p[0]][p[1]])
160                         self.board[x][y].x = p[0]
161                         self.board[x][y].y = p[1]
162
163
164                         self.board[p[0]][p[1]] = self.board[x][y]
165                         self.board[x][y].rank = result[4]
166
167                         self.board[x][y] = None
168                         
169                 elif outcome == "DIES":
170                         if self.board[p[0]][p[1]] == None:
171                                 return False
172
173                         if self.board[x][y].colour == self.colour:
174                                 self.units.remove(self.board[x][y])
175
176                         self.board[p[0]][p[1]].rank = result[5]
177                         self.board[x][y] = None
178                 elif outcome == "BOTHDIE":
179                         if self.board[p[0]][p[1]] == None:
180                                 return False
181
182
183                         if self.board[x][y].colour == self.colour:
184                                 self.units.remove(self.board[x][y])
185                         if self.board[p[0]][p[1]].colour == self.colour:
186                                 self.units.remove(self.board[p[0]][p[1]])
187                         self.board[p[0]][p[1]] = None
188                         self.board[x][y] = None
189                 elif outcome == "FLAG":
190                         #sys.stderr.write("     Game over!\n")
191                         return False
192                 elif outcome == "ILLEGAL":
193                         #sys.stderr.write("     Illegal move!\n")
194                         return False
195                 else:
196                         #sys.stderr.write("     Don't understand outcome \"" + outcome + "\"!\n");
197                         return False
198
199                 #sys.stderr.write("     Completed interpreting move!\n");               
200                 return True
201
202         def debugPrintBoard(self):
203                 for y in range(0, self.height):
204                         for x in range(0, self.width):
205                                 if self.board[x][y] == None:
206                                         sys.stderr.write(".");
207                                 else:
208                                         sys.stderr.write(str(self.board[x][y].rank));
209                         sys.stderr.write("\n")
210                                 
211                         
212
213 asmodeus = Asmodeus()
214

UCC git Repository :: git.ucc.asn.au