code: def unimodality_prox(tensor):
      """
      This function projects each column of the input array on the set of arrays so that
            x[1] <= x[2] <= x[j] >= x[j+1]... >= x[n]
      is satisfied columnwise.
  
      Parameters
      ----------
      tensor : ndarray
  
      Returns
      -------
      ndarray
           A tensor of which columns' distribution are unimodal.
  
      References
      ----------
      .. [1]: Bro, R., & Sidiropoulos, N. D. (1998). Least squares algorithms under
              unimodality and non‐negativity constraints. Journal of Chemometrics:
              A Journal of the Chemometrics Society, 12(4), 223-247.
      """
      if tl.ndim(tensor) == 1:
          tensor = tl.vec_to_tensor(tensor, [tl.shape(tensor)[0], 1])
      elif tl.ndim(tensor) > 2:
          raise ValueError(
              "Unimodality prox doesn't support an input which has more than 2 dimensions."
          )
  
      tensor_unimodal = tl.copy(tensor)
      monotone_increasing = tl.tensor(
          monotonicity_prox(tensor), **tl.context(tensor)
      )
      monotone_decreasing = tl.tensor(
          monotonicity_prox(tensor, decreasing=True),
          **tl.context(tensor),
      )
      # Next line finds mutual peak points
      values = tl.tensor(
          tl.to_numpy((tensor - monotone_decreasing >= 0))
          * tl.to_numpy((tensor - monotone_increasing >= 0)),
          **tl.context(tensor),
      )
  
      sum_inc = tl.where(
          values == 1,
          tl.cumsum(tl.abs(tensor - monotone_increasing), axis=0),
          tl.tensor(0, **tl.context(tensor)),
      )
      sum_inc = tl.where(
          values == 1,
          sum_inc - tl.abs(tensor - monotone_increasing),
          tl.tensor(0, **tl.context(tensor)),
      )
      sum_dec = tl.where(
          tl.flip(values, axis=0) == 1,
          tl.cumsum(
              tl.abs(
                  tl.flip(tensor, axis=0)
                  - tl.flip(monotone_decreasing, axis=0)
              ),
              axis=0,
          ),
          tl.tensor(0, **tl.context(tensor)),
      )
      sum_dec = tl.where(
          tl.flip(values, axis=0) == 1,
          sum_dec
          - tl.abs(
              tl.flip(tensor, axis=0)
              - tl.flip(monotone_decreasing, axis=0)
          ),
          tl.tensor(0, **tl.context(tensor)),
      )
  
      difference = tl.where(
          values == 1,
          sum_inc + tl.flip(sum_dec, axis=0),
          tl.max(sum_inc + tl.flip(sum_dec, axis=0)),
      )
      min_indice = tl.argmin(tl.tensor(difference), axis=0)
  
      for i in range(len(min_indice)):
          tensor_unimodal = tl.index_update(
              tensor_unimodal,
              tl.index[: int(min_indice[i]), i],
              monotone_increasing[: int(min_indice[i]), i],
          )
          tensor_unimodal = tl.index_update(
              tensor_unimodal,
              tl.index[int(min_indice[i] + 1) :, i],
              monotone_decreasing[int(min_indice[i] + 1) :, i],
          )
      return tensor_unimodal
  
file_path: tensorly/tensorly/tenalg/proximal.py
imports: import tensorly
  import numpy
label_desc: Use image node_id 5 for calling a global function with example usage: unimodality_prox(tensor) and returns: tensor_unimodal