code: def _vol_denoise(train, vol_idx, model, data_shape, alpha):
      """Denoise a single 3D volume using a train and test phase.
  
      Parameters
      ----------
      train : ndarray
          Array of all 3D patches flattened out to be 2D.
  
      vol_idx : int
          The volume number that needs to be held out for training.
  
      model : string, or initialized linear model object.
              This will determine the algorithm used to solve the set of linear
              equations underlying this model. If it is a string it needs to be
              one of the following: {'ols', 'ridge', 'lasso'}. Otherwise,
              it can be an object that inherits from
              `dipy.optimize.SKLearnLinearSolver` or an object with a similar
              interface from Scikit-Learn:
              `sklearn.linear_model.LinearRegression`,
              `sklearn.linear_model.Lasso` or `sklearn.linear_model.Ridge`
              and other objects that inherit from `sklearn.base.RegressorMixin`.
              Default: 'ridge'.
  
      data_shape : ndarray
          The 4D shape of noisy DWI data to be denoised.
  
      alpha : float, optional
          Regularization parameter only for ridge and lasso regression models.
          default: 1.0
  
      Returns
      -------
      model prediction : ndarray
          Denoised array of all 3D patches flattened out to be 2D corresponding
          to the held out volume `vol_idx`.
  
      """
      # To add a new model, use the following API
      # We adhere to the following options as they are used for comparisons
      if model.lower() == "ols":
          model = linear_model.LinearRegression(copy_X=False)
  
      elif model.lower() == "ridge":
          model = linear_model.Ridge(copy_X=False, alpha=alpha)
  
      elif model.lower() == "lasso":
          model = linear_model.Lasso(
              copy_X=False, max_iter=50, alpha=alpha
          )
  
      elif (
          isinstance(model, opt.SKLearnLinearSolver)
          or has_sklearn
          and isinstance(model, sklearn.base.RegressorMixin)
      ):
          model = model
  
      else:
          e_s = "The `solver` key-word argument needs to be: "
          e_s += "'ols', 'ridge', 'lasso' or a "
          e_s += "`dipy.optimize.SKLearnLinearSolver` object"
          raise ValueError(e_s)
  
      cur_x, y = _vol_split(train, vol_idx)
      model.fit(cur_x.T, y.T)
  
      return model.predict(cur_x.T).reshape(
          data_shape[0], data_shape[1], data_shape[2]
      )
  
file_path: dipy/dipy/denoise/patch2self.py
imports: import numpy
  from warnings import warn
  import time
  from dipy.utils.optpkg import optional_package
  import dipy.core.optimize
label_desc: Use image node_id 2 for calling a global function with example usage: _vol_denoise(train, vol_idx, model, data_shape, alpha) and returns: model