def test_build_states_invalid_buffer_capacity():
    """
    Test to ensure that the build_states function raises an error if the buffer
    capacity is less than 1
    """
    with pytest.raises(ValueError):
        build_states(
            threshold=None,
            system_capacity=None,
            buffer_capacity=0,
        )
def test_visualise_markov_chain(
    num_of_servers, threshold, system_capacity, buffer_capacity
):
    """
    Test that checks if a neworkx MultiDiGraph object is returned and that the set
    of all nodes used is the same se as the set of all states that the build_states
    function returns.
    """
    all_states = build_states(
        threshold=threshold,
        system_capacity=system_capacity,
        buffer_capacity=buffer_capacity,
    )
    set_of_all_states = set(all_states)

    markov_chain_plot = visualise_markov_chain(
        num_of_servers=num_of_servers,
        threshold=threshold,
        system_capacity=system_capacity,
        buffer_capacity=buffer_capacity,
    )
    set_of_nodes = set(markov_chain_plot.nodes)

    assert isinstance(markov_chain_plot, nx.classes.multidigraph.DiGraph)
    assert set_of_all_states == set_of_nodes
    plt.close()  # TODO Investigate if it's possible to remove this line
def test_get_state_probabilities_array():
    """
    Test to ensure that the sum of elements of the pi array equate to 1
    """
    all_states = build_states(
        threshold=3,
        system_capacity=5,
        buffer_capacity=4,
    )
    transition_matrix = get_transition_matrix(
        lambda_2=0.1,
        lambda_1=0.2,
        mu=0.2,
        num_of_servers=3,
        threshold=3,
        system_capacity=5,
        buffer_capacity=4,
    )
    pi = get_steady_state_algebraically(
        Q=transition_matrix, algebraic_function=np.linalg.solve
    )
    pi_array = get_markov_state_probabilities(
        pi=pi, all_states=all_states, output=np.ndarray
    )

    assert round(np.nansum(pi_array), NUMBER_OF_DIGITS_TO_ROUND) == 1
def test_build_states(threshold, system_capacity, buffer_capacity):
    """
    Test to ensure that the build_states function returns the correct number of
    states, for different integer values of the threshold, system and buffer capacities
    """
    states = build_states(
        threshold=threshold,
        system_capacity=system_capacity,
        buffer_capacity=buffer_capacity,
    )

    if threshold > system_capacity:
        assert len(states) == system_capacity + 1  # +2
    else:
        states_after_threshold = system_capacity - threshold + 1
        size_of_s2 = states_after_threshold if states_after_threshold >= 0 else 0
        all_states_size = size_of_s2 * (buffer_capacity + 1) + threshold
        assert len(states) == all_states_size
def test_get_mean_number_of_individuals_examples():
    """
    Some examples to ensure that the correct mean number of individuals are output
    """
    all_states = build_states(threshold=4, system_capacity=20, buffer_capacity=20)
    transition_matrix = get_transition_matrix(
        lambda_2=0.2,
        lambda_1=0.2,
        mu=0.2,
        num_of_servers=3,
        threshold=4,
        system_capacity=20,
        buffer_capacity=20,
    )
    pi = get_steady_state_algebraically(
        Q=transition_matrix, algebraic_function=np.linalg.solve
    )
    assert (
        round(
            get_mean_number_of_individuals_in_system(pi=pi, states=all_states),
            NUMBER_OF_DIGITS_TO_ROUND,
        )
        == 2.88827497
    )
    assert (
        round(
            get_mean_number_of_individuals_in_service_area(pi=pi, states=all_states),
            NUMBER_OF_DIGITS_TO_ROUND,
        )
        == 2.44439504
    )
    assert (
        round(
            get_mean_number_of_individuals_in_buffer_center(pi=pi, states=all_states),
            NUMBER_OF_DIGITS_TO_ROUND,
        )
        == 0.44387993
    )