"""
Util functions
"""
from random import randrange
from typing import Dict, List, Tuple


def get_random_elem_from_json_table(table: List[Dict]) -> Dict:
    """
    Gets an element from a dict-serialized table
    """
    range_upper = len(table)
    random_index = randrange(0, range_upper)
    return table[random_index]


# TODO: this is basically pseudocode. Need to finalize based on actual dict
# TODO: implement as binary search, just for optimality's sake
def get_elem_in_range_from_json_table(table: List[Dict], index: int) -> Tuple[Dict, int]:
    """
    Gets an element from a dict-serialized table, along with the index
    of its location in the table
    """
    for i in range(len(table)):
        element = table[i]
        range_values = element["range"]
        # because python ranges are non-inclusive and json ranges are inclusive
        range_values[-1] += 1
        lower_range, upper_range = range_values
        # NOTE: may need to adjust
        if index in range(lower_range, upper_range):
            return element, i


def roll(dice_max: int, modifiers: list[int] = None) -> int:
    """

    Handle a dice roll
    
    Args:
        dice_max (int): _description_
        modifiers (list, optional): _description_. Defaults to [].

    Returns:
        int: _description_
    """
    range_upper = dice_max+1
    roll_result = randrange(0, range_upper)
    for modifier in modifiers:
        roll_result += modifier
    return roll_result


def roll_with_advantage(dice_max: int, modifiers: list[int] = None) -> int:
    roll_1 = roll(dice_max, modifiers)
    roll_2 = roll(dice_max, modifiers)
    return max(roll_1, roll_2)


def roll_with_disadvantage(dice_max: int, modifiers: list[int] = None) -> int:
    roll_1 = roll(dice_max, modifiers)
    roll_2 = roll(dice_max, modifiers)
    return min(roll_1, roll_2)
