def prox_l1(v, alpha):
    r"""Compute the proximal operator of the :math:`\ell_1` norm (scalar
    shrinkage/soft thresholding)

     .. math::
      \mathrm{prox}_{\alpha f}(\mathbf{v}) =
      \mathcal{S}_{1,\alpha}(\mathbf{v}) = \mathrm{sign}(\mathbf{v})
      \odot \max(0, |\mathbf{v}| - \alpha)

    where :math:`f(\mathbf{x}) = \|\mathbf{x}\|_1`.

    Unlike the corresponding :func:`norm_l1`, there is no need for an
    `axis` parameter since the proximal operator of the :math:`\ell_1`
    norm is the same when taken independently over each element, or
    over their sum.


    Parameters
    ----------
    v : array_like
      Input array :math:`\mathbf{v}`
    alpha : float or array_like
      Parameter :math:`\alpha`

    Returns
    -------
    x : ndarray
      Output array
    """

    if have_numexpr:
        return ne.evaluate(
            'where(abs(v)-alpha > 0, where(v >= 0, 1, -1) * (abs(v)-alpha), 0)'
        )
    else:
        return np.sign(v) * (np.clip(np.abs(v) - alpha, 0, float('Inf')))
def prox_l1 ( v , alpha ) : if have_numexpr : return ne . evaluate ( 'where(abs(v)-alpha > 0, where(v >= 0, 1, -1) * (abs(v)-alpha), 0)' ) else : return np . sign ( v ) * ( np . clip ( np . abs ( v ) - alpha , 0 , float ( 'Inf' ) ) )
r"""Compute the proximal operator of the :math:`\ell_1` norm (scalar
    shrinkage/soft thresholding)

     .. math::
      \mathrm{prox}_{\alpha f}(\mathbf{v}) =
      \mathcal{S}_{1,\alpha}(\mathbf{v}) = \mathrm{sign}(\mathbf{v})
      \odot \max(0, |\mathbf{v}| - \alpha)

    where :math:`f(\mathbf{x}) = \|\mathbf{x}\|_1`.

    Unlike the corresponding :func:`norm_l1`, there is no need for an
    `axis` parameter since the proximal operator of the :math:`\ell_1`
    norm is the same when taken independently over each element, or
    over their sum.


    Parameters
    ----------
    v : array_like
      Input array :math:`\mathbf{v}`
    alpha : float or array_like
      Parameter :math:`\alpha`

    Returns
    -------
    x : ndarray
      Output array