def search(array, value, dir="-"):
    """
    Searches a sorted (ascending) array for a value, or if value is not found,
    will attempt to find closest value.

    Specifying dir="-" finds index of greatest value in array less than
    or equal to the given value.

    Specifying dir="+" means find index of least value in array greater than
    or equal to the given value.

    Specifying dir="*" means find index of value closest to the given value.
    """

    if value < array[0]:
        if dir == "+":
            return 0

        else:
            raise IndexError(f"No value found before {value}.")

    if value > array[-1]:
        if dir == "-":
            return len(array) - 1

        else:
            raise IndexError(f"No value found after {value}.")

    J = 0
    K = len(array) - 1

    while True:
        if value == array[J]:
            return J

        elif value == array[K]:
            return K

        elif K == J + 1:
            if dir == "-":
                return J

            elif dir == "+":
                return K

            elif dir == "*":
                return min((J, K), key=lambda n: abs(n - value))

        N = (J + K)//2

        if value < array[N]:
            K = N

        elif value > array[N]:
            J = N

        elif value == array[N]:
            return N