Skip to main content

Basic Pop-It package

Project description

PopIt Game Documentation

Overview

The PopIt game is a simple turn-based game where two players take turns popping elements on a 6x6 board. The game is won ehen one player forces the other to make the last move.

Constants

  • FIRST = 1: Represents the first player.
  • SECOND = 2: Represents the second player.
  • NONE = 0: Represents an empty spot on the board.
  • POPPED = 1: Represents a popped spot on the board.
  • NORESULT = 0: Indicates no result.
  • FIRSTWIN = 1: Indicates a win for the first player.
  • SECONDWIN = 2: Indicates a win for the second player.

PopIt Class

Initialization

class PopIt:
    def __init__(self, board=None, turn=FIRST):
        if board is None:
            self.board = [[NONE for _ in range(6)] for _ in range(6)]
        else:
            self.board = board
        self.turn = turn
  • board: A 6x6 matrix representing the game board. Defaults to an empty board if not provided.
  • turn: Indicates the current player's turn. Defaults to FIRST.

Methods

makeMove

def makeMove(self, moveRow, numberOfPops):
    new_board = [row[:] for row in self.board]
    for _ in range(numberOfPops):
        for col in range(6):
            if new_board[moveRow][col] == NONE:
                new_board[moveRow][col] = POPPED
                break
    new_turn = 3 - self.turn
    return PopIt(board=new_board, turn=new_turn)
  • moveRow: The row where the move is made.
  • numberOfPops: The number of pops to make in the specified row.
  • Returns a new PopIt object with the updated board and turn.

Functions

stringToArray

def stringToArray(string):
    if len(string) != 37:
        raise ValueError("Input string must have exactly 37 characters.")
    
    array = []
    for i in range(0, 36, 6):
        row = [int(char) for char in string[i:i+6]]
        array.append(row)
    return array, int(string[36])

string: The current board position in upi position notation, which is a 1d 37 element array, the first 36 elements is the flattened board position while the last character indicates the turn, 1 for 1st player 2 for 2nd player

  • returns a 2d list with the shape of (6, 6), suitable to be fed into the PopPit class to create a PopIt instance

printPopIt

def printPopIt(PopIt, fancy=False):
  for row in range(6):
    print(f"{row + 1} ", end="")
    for col in range(6):
      if fancy:
        if PopIt.board[row][col] == NONE:
          print("🔲", end="")
        else:
          print("⬛", end="")
      else:
        if PopIt.board[row][col] == NONE:
          print("-", end=" ")
        else:
          print("X", end=" ")
    print()
  if fancy:
    print("   1 2 3 4 5 6")
  else:
    print("  1 2 3 4 5 6")
  print()
  • PopIt: The game state to be printed.
  • fancy: Wether to print the fancy board or not (Default False)(Not all terminals support it)
  • Prints the current state of the game board.

moveGen

def moveGen(PopIt):
    return [sum(1 for col in row if col == 0) for row in PopIt.board]
  • PopIt: The game state.
  • Returns a list indicating the number of available pops in each row.

makeMove

def makeMove(PopIt, moveRow, numberOfPops):
    for _ in range(numberOfPops):
        for col in range(6):
            if PopIt.board[moveRow][col] == NONE:
                PopIt.board[moveRow][col] = POPPED
                break
    PopIt.turn = 3 - PopIt.turn
    return PopIt
  • PopIt: The game state.
  • moveRow: The row where the move is made.
  • numberOfPops: The number of pops to make in the specified row.
  • Updates the game state with the specified move and returns the updated state.

boardFull

def boardFull(PopIt):
    for row in range(6):
        for col in range(6):
            if PopIt.board[row][col] == NONE:
                return False
    return True
  • PopIt: The game state.
  • Returns True if the board is full, otherwise False.

getResult

def getResult(PopIt):
    if boardFull(PopIt):
        return PopIt.turn
    elif isCheckMate(PopIt):
        return 3 - PopIt.turn
    return NORESULT
  • PopIt: The game state.
  • Returns the result of the game (FIRSTWIN, SECONDWIN, or NORESULT).

isCheckMate

def isCheckMate(PopIt):
    numPops = 0
    for row in range(6):
        for col in range(6):
            if PopIt.board[row][col] == NONE:
                numPops += 1
                if numPops > 1:
                    return False
    return True
  • PopIt: The game state.
  • Returns True if the game is in a checkmate position, otherwise False.

perfD

def perfD(PopIt, depth):
    if depth == 0:
        return 1
    nodes = 0
    row = 0
    for totalPopsAvail in moveGen(PopIt):
        for numberOfPops in range(1, totalPopsAvail + 1):
            newPopIt = PopIt.makeMove(row, numberOfPops)
            nodes += perfD(newPopIt, depth - 1)
        row += 1
    return nodes
  • PopIt: The game state.
  • depth: The depth to search.
  • Returns the number of nodes at the specified depth.

perfT

def perfT(PopIt, maxDepth):
    startTime = time.time()
    totalNodes = 0
    for depth in range(1, maxDepth + 1):
        totalNodes += perfD(PopIt, depth)
        elapsed = time.time() - startTime
        print(
            f"info string perft depth {depth} nodes {totalNodes} time {int(1000 * elapsed)} nps {int(totalNodes / (elapsed + 0.00000001))}"
        )
  • PopIt: The game state.
  • maxDepth: The maximum depth to search.
  • Performs a perft (performance test) up to the specified depth and prints the results.

Example Usage

Simple examples making use of the Popitto package

Printing move generation

import Popitto.Framework as Popitto
Pop = Popitto.PopIt()
print(Popitto.moveGen(Pop))

Performing a performance test

import Popitto.Framework as Popitto
Pop = Popitto.PopIt()
Popitto.perfT(Pop, 4)

Simple Pop-It Game

import Popitto.Framework as Popitto
Pop = Popitto.PopIt()
while True:
  Popitto.printPopIt(Pop)
  if Popitto.boardFull(Pop):
    print(f"{'First Player' if Popitto.getResult(Pop) == Popitto.FIRST else 'Second Player'} WON!")
    break

  moveRow = input("Select a row (1-6): ")
  numberOfPops = input("Select number of pops: ")
  Pop = Pop.makeMove(int(moveRow) - 1, int(numberOfPops))

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

popitto-0.1.2.tar.gz (3.9 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

Popitto-0.1.2-py3-none-any.whl (4.6 kB view details)

Uploaded Python 3

File details

Details for the file popitto-0.1.2.tar.gz.

File metadata

  • Download URL: popitto-0.1.2.tar.gz
  • Upload date:
  • Size: 3.9 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/5.1.1 CPython/3.12.4

File hashes

Hashes for popitto-0.1.2.tar.gz
Algorithm Hash digest
SHA256 e4cb723ecc0950f7faae13319f5412cda453755c54cf365cf12b0b0f1943afda
MD5 0f4f712bd8e8471ee0b20f2bf0da2811
BLAKE2b-256 4419a941d1b7b27b40f785c6dbf8e05b6af65ffc913fa9d51690b82bec29a858

See more details on using hashes here.

File details

Details for the file Popitto-0.1.2-py3-none-any.whl.

File metadata

  • Download URL: Popitto-0.1.2-py3-none-any.whl
  • Upload date:
  • Size: 4.6 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/5.1.1 CPython/3.12.4

File hashes

Hashes for Popitto-0.1.2-py3-none-any.whl
Algorithm Hash digest
SHA256 713e53fa615e3c8a5e5d58f29796d7a0970e756f94f270c4afe0b21388aa5df0
MD5 47c2706ad36cf9585d12b920ae404400
BLAKE2b-256 aef0da9bf001cc2e72b324fb0c732b4aa29175358a420ea57674b4f5d9e225fb

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page