catanatron.models package#
Submodules#
catanatron.models.actions module#
Move-generation functions (these return a list of actions that can be taken by current player). Main function is generate_playable_actions.
- catanatron.models.actions.inner_maritime_trade_possibilities(hand_freqdeck, bank_freqdeck, port_resources)#
This inner function is to make this logic more shareable
- catanatron.models.actions.ncr(n, r)#
n choose r. helper for discard_possibilities
- catanatron.models.actions.road_building_possibilities(state, color, check_money=True) List[Action] #
catanatron.models.board module#
- class catanatron.models.board.Board(catan_map=None, initialize=True)#
Bases:
object
Encapsulates all state information regarding the board.
- buildings#
Mapping from node id to building (if there is a building there).
- Type
Dict[NodeId, Tuple[Color, FastBuildingType]]
- roads#
Mapping from edge to Color (if there is a road there). Contains inverted edges as well for ease of querying.
- Type
Dict[EdgeId, Color]
- connected_components#
Cache datastructure to speed up maintaining longest road computation. To be queried by Color. Value is a list of node sets.
- Type
Dict[Color, List[Set[NodeId]]]
- board_buildable_ids#
Cache of buildable node ids in board.
- Type
Set[NodeId]
- road_length#
Number of roads of longest road
- Type
int
- robber_coordinate#
Coordinate where robber is.
- Type
Coordinate
- build_city(color, node_id)#
- build_road(color, edge)#
- build_settlement(color, node_id, initial_build_phase=False)#
Adds a settlement, and ensures is a valid place to build.
- Parameters
color (Color) – player’s color
node_id (int) – where to build
initial_build_phase (bool, optional) – Whether this is part of initial building phase, so as to skip connectedness validation. Defaults to True.
- copy()#
- dfs_walk(node_id, color)#
Generates set of nodes that are “connected” to given node.
- Parameters
node_id (int) – Where to start search/walk.
color (Color) – Player color asking
- Returns
- Nodes that are “connected” to this one
by roads of the color player.
- Return type
Set[int]
- find_connected_components(color: Color)#
- Returns
- connected subgraphs. subgraphs
might include nodes that color doesnt own (on the way and on ends), just to make it is “closed” and easier for buildable_nodes to operate.
- Return type
nx.Graph[]
- get_edge_color(edge)#
- get_node_color(node_id)#
- get_player_port_resources(color)#
Yields resources (None for 3:1) of ports owned by color
- is_enemy_node(node_id, color)#
- is_enemy_road(edge, color)#
- is_friendly_node(node_id, color)#
- is_friendly_road(edge, color)#
- catanatron.models.board.get_edges(land_nodes=None)#
- catanatron.models.board.get_node_distances()#
catanatron.models.coordinate_system module#
- class catanatron.models.coordinate_system.Direction(value, names=None, *, module=None, qualname=None, type=None, start=1, boundary=None)#
Bases:
Enum
- EAST = 'EAST'#
- NORTHEAST = 'NORTHEAST'#
- NORTHWEST = 'NORTHWEST'#
- SOUTHEAST = 'SOUTHEAST'#
- SOUTHWEST = 'SOUTHWEST'#
- WEST = 'WEST'#
- catanatron.models.coordinate_system.add(acoord, bcoord)#
- catanatron.models.coordinate_system.cube_to_axial(cube)#
- catanatron.models.coordinate_system.cube_to_offset(cube)#
- catanatron.models.coordinate_system.generate_coordinate_system(num_layers)#
Generates a set of coordinates by expanding outward from a center tile on (0,0,0) with the given number of layers (as in an onion :)). Follows BFS.
- catanatron.models.coordinate_system.num_tiles_for(layer)#
Including inner-layer tiles
- catanatron.models.coordinate_system.offset_to_cube(offset)#
catanatron.models.decks module#
Providers helper functions to deal with representations of decks of cards
We use a histogram / ‘frequency list’ to represent decks (aliased ‘freqdeck’). This representation is concise, easy to copy, access and fast to compare.
- catanatron.models.decks.draw_from_listdeck(list1: List, amount: int, card: int)#
- catanatron.models.decks.freqdeck_add(list1, list2)#
- catanatron.models.decks.freqdeck_can_draw(freqdeck, amount: int, card: Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE'])#
- catanatron.models.decks.freqdeck_contains(list1, list2)#
True if list1 >= list2 element-wise
- catanatron.models.decks.freqdeck_count(freqdeck, card: Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE'])#
- catanatron.models.decks.freqdeck_draw(freqdeck, amount: int, card: Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE'])#
- catanatron.models.decks.freqdeck_from_listdeck(listdeck: Iterable[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']])#
- catanatron.models.decks.freqdeck_replenish(freqdeck, amount: int, card: Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE'])#
- catanatron.models.decks.freqdeck_subtract(list1, list2)#
- catanatron.models.decks.starting_devcard_bank()#
Returns listdeck of devcards
- catanatron.models.decks.starting_devcard_proba(card: Literal['KNIGHT', 'YEAR_OF_PLENTY', 'MONOPOLY', 'ROAD_BUILDING', 'VICTORY_POINT'])#
- catanatron.models.decks.starting_resource_bank()#
Returns freqdeck of resource cards
catanatron.models.enums module#
- class catanatron.models.enums.Action(color, action_type, value)#
Bases:
tuple
Main class to represent action. Should be immutable.
The “value” is a polymorphic field that acts as the “parameters” for the “action_type”. e.g. where to ActionType.BUILD_SETTLEMENT or who to steal from in a ActionType.MOVE_ROBBER action.
We use this class to represent both the _intent_ of say “moving a robber to Tile (0,0,0) and stealing from Blue” as well as the final result of such a move. In moves like these where the intent is not enough to be used to reproduce the game identically, we use “None”s in the “value” container as placeholders for that information needed for fully reproducing a game. (e.g. card stolen, dev card bought, etc…)
See more on ActionType.
- action_type#
Alias for field number 1
- color#
Alias for field number 0
- value#
Alias for field number 2
- class catanatron.models.enums.ActionPrompt(value, names=None, *, module=None, qualname=None, type=None, start=1, boundary=None)#
Bases:
Enum
- BUILD_INITIAL_ROAD = 'BUILD_INITIAL_ROAD'#
- BUILD_INITIAL_SETTLEMENT = 'BUILD_INITIAL_SETTLEMENT'#
- DECIDE_ACCEPTEES = 'DECIDE_ACCEPTEES'#
- DECIDE_TRADE = 'DECIDE_TRADE'#
- DISCARD = 'DISCARD'#
- MOVE_ROBBER = 'MOVE_ROBBER'#
- PLAY_TURN = 'PLAY_TURN'#
- class catanatron.models.enums.ActionType(value, names=None, *, module=None, qualname=None, type=None, start=1, boundary=None)#
Bases:
Enum
Type of action taken by a player.
See comments next to each ActionType for the shape of the corresponding .value field in Actions of that type.
- ACCEPT_TRADE = 'ACCEPT_TRADE'#
- BUILD_CITY = 'BUILD_CITY'#
- BUILD_ROAD = 'BUILD_ROAD'#
- BUILD_SETTLEMENT = 'BUILD_SETTLEMENT'#
- BUY_DEVELOPMENT_CARD = 'BUY_DEVELOPMENT_CARD'#
- CANCEL_TRADE = 'CANCEL_TRADE'#
- CONFIRM_TRADE = 'CONFIRM_TRADE'#
- DISCARD = 'DISCARD'#
- END_TURN = 'END_TURN'#
- MARITIME_TRADE = 'MARITIME_TRADE'#
- MOVE_ROBBER = 'MOVE_ROBBER'#
- OFFER_TRADE = 'OFFER_TRADE'#
- PLAY_KNIGHT_CARD = 'PLAY_KNIGHT_CARD'#
- PLAY_MONOPOLY = 'PLAY_MONOPOLY'#
- PLAY_ROAD_BUILDING = 'PLAY_ROAD_BUILDING'#
- PLAY_YEAR_OF_PLENTY = 'PLAY_YEAR_OF_PLENTY'#
- REJECT_TRADE = 'REJECT_TRADE'#
- ROLL = 'ROLL'#
catanatron.models.map module#
- class catanatron.models.map.CatanMap(tiles: Dict[Tuple[int, int, int], Union[LandTile, Port, Water]] = {}, land_tiles: Dict[Tuple[int, int, int], LandTile] = {}, port_nodes: Dict[Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']], Set[int]] = {}, land_nodes: FrozenSet[int] = frozenset({}), adjacent_tiles: Dict[int, List[LandTile]] = {}, node_production: Dict[int, Counter] = {}, tiles_by_id: Dict[int, LandTile] = {}, ports_by_id: Dict[int, Port] = {})#
Bases:
object
Represents a randomly initialized map.
- static from_template(map_template: MapTemplate)#
- class catanatron.models.map.LandTile(id: int, resource: Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']], number: Optional[int], nodes: Dict[catanatron.models.enums.NodeRef, int], edges: Dict[catanatron.models.enums.EdgeRef, Tuple[int, int]])#
Bases:
object
- id: int#
- number: Optional[int]#
- resource: Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']]#
- catanatron.models.map.MINI_MAP_TEMPLATE = MapTemplate(numbers=[3, 4, 5, 6, 8, 9, 10], port_resources=[], tile_resources=['WOOD', None, 'BRICK', 'SHEEP', 'WHEAT', 'WHEAT', 'ORE'], topology={(0, 0, 0): <class 'catanatron.models.map.LandTile'>, (1, -1, 0): <class 'catanatron.models.map.LandTile'>, (0, -1, 1): <class 'catanatron.models.map.LandTile'>, (-1, 0, 1): <class 'catanatron.models.map.LandTile'>, (-1, 1, 0): <class 'catanatron.models.map.LandTile'>, (0, 1, -1): <class 'catanatron.models.map.LandTile'>, (1, 0, -1): <class 'catanatron.models.map.LandTile'>, (2, -2, 0): <class 'catanatron.models.map.Water'>, (1, -2, 1): <class 'catanatron.models.map.Water'>, (0, -2, 2): <class 'catanatron.models.map.Water'>, (-1, -1, 2): <class 'catanatron.models.map.Water'>, (-2, 0, 2): <class 'catanatron.models.map.Water'>, (-2, 1, 1): <class 'catanatron.models.map.Water'>, (-2, 2, 0): <class 'catanatron.models.map.Water'>, (-1, 2, -1): <class 'catanatron.models.map.Water'>, (0, 2, -2): <class 'catanatron.models.map.Water'>, (1, 1, -2): <class 'catanatron.models.map.Water'>, (2, 0, -2): <class 'catanatron.models.map.Water'>, (2, -1, -1): <class 'catanatron.models.map.Water'>})#
Standard 4-player map
- class catanatron.models.map.MapTemplate(numbers: List[int], port_resources: List[Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']]], tile_resources: List[Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']]], topology: Mapping[Tuple[int, int, int], Union[Type[catanatron.models.map.LandTile], Type[catanatron.models.map.Water], Tuple[Type[catanatron.models.map.Port], catanatron.models.coordinate_system.Direction]]])#
Bases:
object
- numbers: List[int]#
- port_resources: List[Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']]]#
- tile_resources: List[Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']]]#
- class catanatron.models.map.Port(id: int, resource: Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']], direction: catanatron.models.coordinate_system.Direction, nodes: Dict[catanatron.models.enums.NodeRef, int], edges: Dict[catanatron.models.enums.EdgeRef, Tuple[int, int]])#
Bases:
object
- id: int#
- resource: Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']]#
- class catanatron.models.map.Water(nodes: Dict[catanatron.models.enums.NodeRef, int], edges: Dict[catanatron.models.enums.EdgeRef, Tuple[int, int]])#
Bases:
object
- catanatron.models.map.build_dice_probas()#
- catanatron.models.map.build_map(map_type: Literal['BASE', 'TOURNAMENT', 'MINI'])#
- catanatron.models.map.get_edge_nodes(edge_ref)#
returns pair of nodes at the “ends” of a given edge
- catanatron.models.map.get_node_counter_production(adjacent_tiles: Dict[int, List[LandTile]], node_id: int)#
- catanatron.models.map.get_nodes_and_edges(tiles, coordinate: Tuple[int, int, int], node_autoinc)#
Get pre-existing nodes and edges in board for given tile coordinate
- catanatron.models.map.init_adjacent_tiles(land_tiles: Dict[Tuple[int, int, int], LandTile]) Dict[int, List[LandTile]] #
- catanatron.models.map.init_node_production(adjacent_tiles: Dict[int, List[LandTile]]) Dict[int, Counter] #
Returns node_id => Counter({WHEAT: 0.123, …})
- catanatron.models.map.init_port_nodes_cache(tiles: Dict[Tuple[int, int, int], Union[LandTile, Port, Water]]) Dict[Optional[Literal['WOOD', 'BRICK', 'SHEEP', 'WHEAT', 'ORE']], Set[int]] #
Initializes board.port_nodes cache.
- Parameters
tiles (Dict[Coordinate, Tile]) – initialized tiles datastructure
- Returns
- Mapping from FastResource to node_ids that
enable port trading. None key represents 3:1 port.
- Return type
Dict[Union[FastResource, None], Set[int]]
- catanatron.models.map.initialize_tiles(map_template: MapTemplate, shuffled_numbers_param=None, shuffled_port_resources_param=None, shuffled_tile_resources_param=None) Dict[Tuple[int, int, int], Union[LandTile, Port, Water]] #
Initializes a new random board, based on the MapTemplate.
It first shuffles tiles, ports, and numbers. Then goes satisfying the topology (i.e. placing tiles on coordinates); ensuring to “attach” these to neighbor tiles (so as to not repeat nodes or edges objects).
- Parameters
map_template (MapTemplate) – Template to initialize.
- Raises
ValueError – Invalid tile in topology
- Returns
Coordinate to initialized Tile mapping.
- Return type
Dict[Coordinate, Tile]
- catanatron.models.map.number_probability(number)#
catanatron.models.player module#
- class catanatron.models.player.Color(value, names=None, *, module=None, qualname=None, type=None, start=1, boundary=None)#
Bases:
Enum
Enum to represent the colors in the game
- BLUE = 'BLUE'#
- ORANGE = 'ORANGE'#
- RED = 'RED'#
- WHITE = 'WHITE'#
- class catanatron.models.player.HumanPlayer(color, is_bot=True)#
Bases:
Player
Human player that selects which action to take using standard input
- class catanatron.models.player.Player(color, is_bot=True)#
Bases:
object
Interface to represent a player’s decision logic.
Formulated as a class (instead of a function) so that players can have an initialization that can later be serialized to the database via pickle.
- decide(game, playable_actions)#
Should return one of the playable_actions or an OFFER_TRADE action if its your turn and you have already rolled.
- reset_state()#
Hook for resetting state between games
- class catanatron.models.player.RandomPlayer(color, is_bot=True)#
Bases:
Player
Random AI player that selects an action randomly from the list of playable_actions