docstr: Use LU decomposition to compute inverse of matrix.
  Given a square matrix A:
  P, L, U = lu(A)
  b_eye is an identity matrix with the same shape as matrix A, then,
  (P * L * U) * A_inv = b_eye
  L * (U * A_inv) = P.T * b_eye
  use `solve_triangular` twice to compute the inverse of matrix A.
docstr_tok: ["Use","LU","decomposition","to","compute","inverse","of","matrix",".","Given","a","square","matrix","A",":","P",",","L",",","U","=","lu","(","A",")","b_eye","is","an","identity","matrix","with","the","same","shape","as","matrix","A",",","then",",","(","P","*","L","*","U",")","*","A_inv","=","b_eye","L","*","(","U","*","A_inv",")","=","P.T","*","b_eye","use","`","solve_triangular","`","twice","to","compute","the","inverse","of","matrix","A","."]
code: def tile(cls, op):
      """
      Use LU decomposition to compute inverse of matrix.
      Given a square matrix A:
      P, L, U = lu(A)
      b_eye is an identity matrix with the same shape as matrix A, then,
      (P * L * U) * A_inv = b_eye
      L * (U * A_inv) = P.T * b_eye
      use `solve_triangular` twice to compute the inverse of matrix A.
      """
      from .lu import lu
      from ..datasource import eye
      from ..base.transpose import TensorTranspose
      from .tensordot import tensordot
      from .solve_triangular import solve_triangular
  
      in_tensor = op.input
      is_sparse = in_tensor.is_sparse()
  
      if len(in_tensor.chunks) == 1:
          return cls._tile_one_chunk(op)
  
      b_eye = eye(
          in_tensor.shape[0],
          chunk_size=in_tensor.nsplits,
          sparse=is_sparse,
      )
  
      p, l, u = lu(in_tensor)
  
      # transposed p equals to inverse of p
      p_transpose = TensorTranspose(
          dtype=p.dtype,
          sparse=p.op.sparse,
          axes=list(range(in_tensor.ndim))[::-1],
      ).new_tensor([p], p.shape)
  
      b = tensordot(
          p_transpose,
          b_eye,
          axes=((p_transpose.ndim - 1,), (b_eye.ndim - 2,)),
      )
  
      # as `l` is a lower matrix, `lower=True` should be specified.
      uy = solve_triangular(l, b, lower=True, sparse=op.sparse)
  
      a_inv = solve_triangular(u, uy, sparse=op.sparse)
      a_inv = yield from recursive_tile(a_inv)
      return [a_inv]
  
file_path: mars/mars/tensor/linalg/inv.py
imports: import numpy
  from numpy.linalg import LinAlgError
  from ...None import opcodes
  from ...core import recursive_tile
  from ...serialization.serializables import KeyField
  from ..array_utils import as_same_device, device
  from ..datasource import tensor
  from ..operands import TensorHasInput, TensorOperandMixin
  from ..core import TensorOrder
label_desc: Use image node_id 3 for calling the TensorInv obj's underlying member method code with example usage: obj.tile(cls, op) and returns: list, cls