code: def cholesky(A, sparse=True, verbose=True):
      
      if SKSPIMPORT:
          A = sp.sparse.csc_matrix(A)
          try:
              F = spcholesky(A)
  
              # permutation matrix P
              P = sp.sparse.lil_matrix(A.shape)
              p = F.P()
              P[np.arange(len(p)), p] = 1
  
              # permute
              L = F.L()
              L = P.T.dot(L)
          except CholmodNotPositiveDefiniteError as e:
              raise NotPositiveDefiniteError('Matrix is not positive definite')
  
          if sparse:
              return L.T # upper triangular factorization
          return L.T.A # upper triangular factorization
  
      else:
          msg = 'Could not import Scikit-Sparse or Suite-Sparse.\n'\
                'This will slow down optimization for models with '\
                'monotonicity/convexity penalties and many splines.\n'\
                'See installation instructions for installing '\
                'Scikit-Sparse and Suite-Sparse via Conda.'
          if verbose:
              warnings.warn(msg)
  
          if sp.sparse.issparse(A):
              A = A.A
  
          try:
              L = sp.linalg.cholesky(A, lower=False)
          except LinAlgError as e:
              raise NotPositiveDefiniteError('Matrix is not positive definite')
  
          if sparse:
              return sp.sparse.csc_matrix(L)
          return L
docs: Choose the best possible cholesky factorizor.
  
      if possible, import the Scikit-Sparse sparse Cholesky method.
      Permutes the output L to ensure A = L.H . L
  
      otherwise defaults to numpy's non-sparse version
  
      Parameters
      ----------
      A : array-like
          array to decompose
      sparse : boolean, default: True
          whether to return a sparse array
      verbose : bool, default: True
          whether to print warnings