def diag(self): """ Return a vector with the diagonal elements of the matrix. """ N = self.nrows data = self.flat return asvector([data.flat[i * N + i] for i in range(N)])
def solve_jacobi(self, b, tol=1e-3, x0=None, maxiter=1000): """ Solve a linear using Gauss-Jacobi method. """ b = asvector(b) x = b * 0 D = self.from_diag([1.0 / x for x in self.diag()]) R = self.drop_diag() for _ in range(maxiter): x, old = D * (b - R * x), x if (x - old).norm() < tol: break return x
def solve_triangular(self, b, lower=False): """ Solve a triangular system. If lower=True, it assumes a lower triangular matrix, otherwise (default) assumes an upper triangular matrix. """ N = self.nrows x = [0] * N if lower: for i in range(N): x[i] = (b[i] - self[i].dot(x)) / self[i, i] else: for i in range(N - 1, -1, -1): x[i] = (b[i] - self[i].dot(x)) / self[i, i] return asvector(x)