Skip to content

Commit

Permalink
Testing & Refactor
Browse files Browse the repository at this point in the history
  • Loading branch information
Bytestorm5 committed Apr 12, 2024
1 parent 6ed4e52 commit baa85f0
Show file tree
Hide file tree
Showing 2 changed files with 70 additions and 34 deletions.
92 changes: 61 additions & 31 deletions buckshot_roulette/ai.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,33 @@
from typing import Literal
from dataclasses import asdict
import random
import abc
import typing

class AbstractEngine(abc.ABC):
def __init__(self, playing_as: Literal[0, 1]):
self.me = playing_as

class Dealer:
@abc.abstractmethod
def choice(self, board:BuckshotRoulette):
"""Determines what move this model takes from this given board position
Args:
board (BuckshotRoulette): The current game state
"""
pass

@abc.abstractmethod
def post(self, last_move, result):
"""Any post-processing steps that the model needs to make after a move has been made. Typically used to store results of the magnifying glass and burner phone.
Args:
last_move (str): The move that the engine just made
result (Any): The output of board.make_move
"""
pass

class Dealer(AbstractEngine):
def __init__(self, playing_as: Literal[0, 1]):
self.me = playing_as
self.known_shells: list[bool] = None
Expand Down Expand Up @@ -36,15 +61,16 @@ def _figure_out_shell(self, board: BuckshotRoulette):

return False

def make_move(self, board: BuckshotRoulette):
def choice(self, board: BuckshotRoulette):
if self.known_shells == None:
self.known_shells = [False] * len(board._shotgun)
self.known_shells[-1] = True
list_diff = len(self.known_shells) - len(board._shotgun)
if list_diff < 0:
self.known_shells.extend([False] * -list_diff)
if list_diff > 0:
self.known_shells = self.known_shells[:-list_diff]
# Should basically never be a difference > 1
self.known_shells = self.known_shells[list_diff:]

if self.known_shell == None:
if self._figure_out_shell(board):
Expand All @@ -60,25 +86,22 @@ def make_move(self, board: BuckshotRoulette):
self.known_shell = board._shotgun[0]
self.target = 'op' if self.known_shell else 'self'

using_adrenaline = board.items[self.me].adrenaline > 0
using_medicine = None
has_cigs = board.items[self.me].cigarettes > 0
wants_to_use = None

moves = board.legal_items()
for item in board.POSSIBLE_ITEMS:
if item in moves and board.items[self.me][item] < 1 and (board.items[self.me].adrenaline < 1 or board.items[1][item] < 1):
moves.remove(item)

for item in moves:
if item == 'magnifying_glass' and self.known_shell == None and len(board._shotgun) != 1:
wants_to_use = item
break
if item == 'cigarettes' and board.charges[self.me] < board.max_charges:
wants_to_use = item
has_cigs = False
break
if item == 'meds' and board.charges[1 - self.me] < board.max_charges and not has_cigs and not using_medicine:
if item == 'meds' and board.charges[1 - self.me] < board.max_charges and not 'cigarettes' in moves and not using_medicine:
wants_to_use = item
using_medicine = True
break
Expand All @@ -99,39 +122,46 @@ def make_move(self, board: BuckshotRoulette):
wants_to_use = item
self.known_shell = True
break

main_loop_finished = wants_to_use == None
has_saw = board.items[self.me].saw > 0
if main_loop_finished and 'saw' in moves and self.known_shell == True:

if wants_to_use == None and 'saw' in moves and self.known_shell == True:
decision = random.random() > 0.5
if decision:
self.target = 'self'
else:
self.target = 'op'
wants_to_use = 'saw'
if wants_to_use != None:
if using_adrenaline and board.items[self.me][wants_to_use] < 1:
board.make_move('adrenaline')
result, _ = board.make_move(wants_to_use)
match wants_to_use:
case 'magnifying_glass':
self.known_shells[0] = True
self.known_shell = board._shotgun[0]
pass
case 'beer':
self.known_shells = self.known_shells[1:]
pass
case 'burner_phone':
self.known_shells[result[0]] = True
if 'adrenaline' in moves and board.items[self.me][wants_to_use] < 1:
return 'adrenaline'
return wants_to_use
else:
if self.target == None:
decision = random.random() > 0.5
if decision:
board.make_move('op')
return 'op'
else:
board.make_move('self')
return 'self'
else:
board.make_move(self.target)
self.target = None
self.known_shells = self.known_shells[1:]
self.known_shell = board._shotgun[0] if len(self.known_shells) > 0 and self.known_shells[0] else None
return self.target

def post(self, last_move, move_result):
if last_move in ['op', 'self']:
self.target = None

match last_move:
case 'magnifying_glass':
self.known_shells[0] = True
self.known_shell = move_result
pass
case 'burner_phone':
self.known_shells[move_result[0]] = True

class Random(AbstractEngine):
def __init__(self, playing_as):
pass

def choice(self, board: BuckshotRoulette):
return random.choice(board.moves())

def post(self, last_move, res):
pass
12 changes: 9 additions & 3 deletions buckshot_roulette/game.py
Original file line number Diff line number Diff line change
Expand Up @@ -144,13 +144,19 @@ def moves(self):
for item in self.POSSIBLE_ITEMS:
if items[item] > 0 and self._active_items[item] == 0:
moves.append(item)

if len(moves) == 0:
# Only possible if the previous move is adrenaline, and there are no valid items to take
# Unfortunate.
self._active_items.adrenaline = 0
return self.moves()
return moves

def make_move(self, move, load_new = True):
out_val = None
if self._active_items.adrenaline > 0:
items = self.items[self.opponent()]
self._active_items.adrenaline -= 1
self._active_items.adrenaline = 0
else:
items = self.items[self.current_turn]
match move:
Expand Down Expand Up @@ -202,9 +208,9 @@ def make_move(self, move, load_new = True):
if load_new and len(self._shotgun) == 0:
self.current_turn = 0
self.new_rounds()
return out_val, True
return out_val

return out_val, len(self._shotgun) == 0
return out_val

def live_round(self):
return self._shotgun[0]
Expand Down

0 comments on commit baa85f0

Please sign in to comment.