Generate a DiscreteDP randomly. The reward values are drawn from the
    normal distribution with mean 0 and standard deviation `scale`.

    Parameters
    ----------
    num_states : scalar(int)
        Number of states.

    num_actions : scalar(int)
        Number of actions.

    beta : scalar(float), optional(default=None)
        Discount factor. Randomly chosen from [0, 1) if not specified.

    k : scalar(int), optional(default=None)
        Number of possible next states for each state-action pair. Equal
        to `num_states` if not specified.

    scale : scalar(float), optional(default=1)
        Standard deviation of the normal distribution for the reward
        values.

    sparse : bool, optional(default=False)
        Whether to store the transition probability array in sparse
        matrix form.

    sa_pair : bool, optional(default=False)
        Whether to represent the data in the state-action pairs
        formulation. (If `sparse=True`, automatically set `True`.)

    random_state : int or np.random.RandomState, optional
        Random seed (integer) or np.random.RandomState instance to set
        the initial state of the random number generator for
        reproducibility. If None, a randomly initialized RandomState is
        used.

    Returns
    -------
    ddp : DiscreteDP
        An instance of DiscreteDP.

def random_discrete_dp(num_states, num_actions, beta=None,
               k=None, scale=1, sparse=False, sa_pair=False,
               random_state=None):
    """
    Generate a DiscreteDP randomly. The reward values are drawn from the
    normal distribution with mean 0 and standard deviation `scale`.

    Parameters
    ----------
    num_states : scalar(int)
        Number of states.

    num_actions : scalar(int)
        Number of actions.

    beta : scalar(float), optional(default=None)
        Discount factor. Randomly chosen from [0, 1) if not specified.

    k : scalar(int), optional(default=None)
        Number of possible next states for each state-action pair. Equal
        to `num_states` if not specified.

    scale : scalar(float), optional(default=1)
        Standard deviation of the normal distribution for the reward
        values.

    sparse : bool, optional(default=False)
        Whether to store the transition probability array in sparse
        matrix form.

    sa_pair : bool, optional(default=False)
        Whether to represent the data in the state-action pairs
        formulation. (If `sparse=True`, automatically set `True`.)

    random_state : int or np.random.RandomState, optional
        Random seed (integer) or np.random.RandomState instance to set
        the initial state of the random number generator for
        reproducibility. If None, a randomly initialized RandomState is
        used.

    Returns
    -------
    ddp : DiscreteDP
        An instance of DiscreteDP.

    """
    if sparse:
        sa_pair = True

    # Number of state-action pairs
    L = num_states * num_actions

    random_state = check_random_state(random_state)
    R = scale * random_state.randn(L)
    Q = _random_stochastic_matrix(L, num_states, k=k,
                                  sparse=sparse, format='csr',
                                  random_state=random_state)
    if beta is None:
        beta = random_state.random_sample()

    if sa_pair:
        s_indices, a_indices = sa_indices(num_states, num_actions)
    else:
        s_indices, a_indices = None, None
        R.shape = (num_states, num_actions)
        Q.shape = (num_states, num_actions, num_states)

    ddp = DiscreteDP(R, Q, beta, s_indices, a_indices)
    return ddp