| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206 |
- '''
- >> https://www.codingame.com/ide/173171838252e7c6fd6f3ff9cb8169431a08eec1
- @author: olivier.massot, may 2019
- '''
- import sys
- import time
- debug = True
- t0 = time.time()
- def log(*msg):
- if debug:
- print("{} - ".format(str(time.time() - t0)[1:5]), *msg, file=sys.stderr)
- class Base():
- def __repr__(self):
- return f"<{self.__class__.__name__}: {self.__dict__}>"
- class BaseLoc(Base):
- def __init__(self, x, y):
- self.x = x
- self.y = y
-
- @property
- def pos(self):
- return self.x, self.y
- class Mine(BaseLoc):
- def __init__(self, x, y):
- super().__init__(x, y)
- class BaseOwnedLoc(BaseLoc):
- def __init__(self, x, y, owner):
- super().__init__(x, y)
- self.owner = owner
- @property
- def owned(self):
- return self.owner == 0
- class Building(BaseOwnedLoc):
- def __init__(self, owner, type_, x, y):
- super().__init__(x, y, owner)
- self.type_ = type_
- class Unit(BaseOwnedLoc):
- def __init__(self, owner, id_, level, x, y):
- super().__init__(x, y, owner)
- self.id_ = id_
- self.level = level
-
- class Player(Base):
- def __init__(self, id_):
- self.id_ = id_
- self.gold = 0
- self.income = 0
- self.units = []
- self.buildings = []
- self.hq = None
- def update(self, gold, income, units, buildings):
- self.gold = gold
- self.income = income
- self.units = [u for u in units if u.owner == self.id_]
- self.buildings = [b for b in buildings if b.owner == self.id_]
- class Cell(Base):
- def __init__(self, x, y):
- self.x = x
- self.y = y
- self._content = "#"
- self.unit = None
- self.building = None
-
- @property
- def pos(self):
- return self.x, self.y
-
- @property
- def raw_val(self):
- return self._content
- def update(self, content, unit = None, building = None):
- self._content = content
- self.unit = unit
- self.building = building
-
- @property
- def movable(self):
- return self._content != "#"
-
- @property
- def owned(self):
- return self._content.lower() == "o"
-
- @property
- def opponents(self):
- return self._content.lower() == "x"
-
- @property
- def headquarter(self):
- return self.pos in Grid.hqs
-
- @property
- def occupied(self):
- return self.unit or self.building
-
- @property
- def is_active(self):
- return self._content.isupper()
-
- class Grid(Base):
- dim = 12
- hqs = [(0,0), (11,11)]
-
- def __init__(self, mines = []):
- self.cells = {(x, y): Cell(x, y) for x in range(Grid.dim) for y in range(Grid.dim)}
- self.units = {}
- self.buildings = {}
- self.mines = {(m.x, m.y): m for m in mines}
-
- def print_grid(self):
- return "\n".join(["".join([c for c in row]) for row in self.grid])
-
- @property
- def pos(self):
- return self.x, self.y
-
- @property
- def grid(self):
- return [[self.cells[(x, y)].raw_val for x in range(Grid.dim)] for y in range(Grid.dim)]
- def __getitem__(self, key):
- return self.cells[key]
- def update(self, grid, buildings, units):
- self.buildings = {(b.x, b.y): b for b in buildings}
- self.units = {(u.x, u.y): u for u in units}
-
- for y, row in enumerate(grid):
- for x, c in enumerate(row):
- self.cells[(x, y)].update(c,
- self.units.get((x, y), None),
- self.buildings.get((x, y), None))
- def neighbors(self, x, y, diags=True):
- neighs = [(x, y - 1), (x - 1, y), (x + 1, y), (x, y + 1)]
- if diags:
- neighs += [(x - 1, y - 1), (x + 1, y - 1), (x - 1, y + 1), (x + 1, y + 1)]
- return [(x, y) for x, y in neighs if 0 <= x < Grid.dim and 0 <= y < Grid.dim]
-
- def where_to_train(self):
- available = set()
- for p, c in self.cells.items():
- if c.owned:
- available.add(p)
- available |= set(self.neighbors(*p))
- return (self.cells[p] for p in available if not self.cells[p].occupied)
- mines = [Mine(*[int(j) for j in input().split()]) for _ in range(int(input()))]
- log(f"* mines: {mines}")
- grid = Grid()
- player = Player(0)
- opponent = Player(1)
- while True:
-
- # <--- get input
- gold, income = int(input()), int(input())
- opponent_gold, opponent_income = int(input()), int(input())
- new_grid = [list(input()) for _ in range(12)]
-
- buildings = [Building(*[int(j) for j in input().split()]) for _ in range(int(input()))]
- log(f"* buildings: {buildings}")
- units = [Unit(*[int(j) for j in input().split()]) for _ in range(int(input()))]
- log(f"* units: {units}")
- # --->
-
- # <--- update data
- grid.update(new_grid, buildings, units)
- log(f"grid:\n{grid.print_grid()}")
-
- player.update(gold, income, units, buildings)
- if player.hq is None:
- player.hq = next((c for c in [grid[(x, y)] for x, y in Grid.hqs] if c.owned))
- log(f"player:\n{player}")
-
- opponent.update(opponent_gold, opponent_income, units, buildings)
- if opponent.hq is None:
- opponent.hq = next((c for c in [grid[(x, y)] for x, y in Grid.hqs] if c.opponents))
- log(f"opponent:\n{opponent}")
- # --->
-
- # start
-
- if not player.units:
- c = next(grid.where_to_train())
- print(f"TRAIN 1 {c.x} {c.y}")
-
-
- print("WAIT")
|