Round to the next 0.5-value.

    This function applies the round function `func` to round `n` to the
    next 0.5-value with respect to its exponent with base 10 (i.e.
    1.3e-4 will be rounded to 1.5e-4) if `exp` is None or with respect
    to the given exponent in `exp`.

    Parameters
    ----------
    n: numpy.ndarray
        number to round
    exp: int or numpy.ndarray
        Exponent for rounding. If None, it will be computed from `n` to be the
        exponents for base 10.
    mode: {'s', 'l'}
        rounding mode. If 's', it will be rounded to value whose absolute
        value is below `n`, if 'l' it will rounded to the value whose absolute
        value is above `n`.

    Returns
    -------
    numpy.ndarray
        rounded `n`

    Examples
    --------
    The effects of the different parameters are show in the example below::

        >>> from psyplot.plotter.simple import round_to_05
        >>> a = [-100.3, 40.6, 8.7, -0.00023]
        >>>round_to_05(a, mode='s')
        array([ -1.00000000e+02,   4.00000000e+01,   8.50000000e+00,
                -2.00000000e-04])

        >>> round_to_05(a, mode='l')
        array([ -1.50000000e+02,   4.50000000e+01,   9.00000000e+00,
                -2.50000000e-04])

def round_to_05(n, exp=None, mode='s'):
    """
    Round to the next 0.5-value.

    This function applies the round function `func` to round `n` to the
    next 0.5-value with respect to its exponent with base 10 (i.e.
    1.3e-4 will be rounded to 1.5e-4) if `exp` is None or with respect
    to the given exponent in `exp`.

    Parameters
    ----------
    n: numpy.ndarray
        number to round
    exp: int or numpy.ndarray
        Exponent for rounding. If None, it will be computed from `n` to be the
        exponents for base 10.
    mode: {'s', 'l'}
        rounding mode. If 's', it will be rounded to value whose absolute
        value is below `n`, if 'l' it will rounded to the value whose absolute
        value is above `n`.

    Returns
    -------
    numpy.ndarray
        rounded `n`

    Examples
    --------
    The effects of the different parameters are show in the example below::

        >>> from psyplot.plotter.simple import round_to_05
        >>> a = [-100.3, 40.6, 8.7, -0.00023]
        >>>round_to_05(a, mode='s')
        array([ -1.00000000e+02,   4.00000000e+01,   8.50000000e+00,
                -2.00000000e-04])

        >>> round_to_05(a, mode='l')
        array([ -1.50000000e+02,   4.50000000e+01,   9.00000000e+00,
                -2.50000000e-04])"""
    n = np.asarray(n)
    if exp is None:
        exp = np.floor(np.log10(np.abs(n)))  # exponent for base 10
    ntmp = np.abs(n)/10.**exp  # mantissa for base 10
    if mode == 's':
        n1 = ntmp
        s = 1.
        n2 = nret = np.floor(ntmp)
    else:
        n1 = nret = np.ceil(ntmp)
        s = -1.
        n2 = ntmp
    return np.where(n1 - n2 > 0.5, np.sign(n)*(nret + s*0.5)*10.**exp,
                    np.sign(n)*nret*10.**exp)