void reduce_row_vectors(matrix<T>& M) { bool reiterate = true; while (reiterate) { reiterate = false; for (int v=0; v<M.rows; ++v) for (int w=0; w<M.rows; ++w) if (v!=w) { bool covered = true; for (int i=0; i<M.columns; ++i) if (M.data[v][i] > M.data[w][i]) { covered = false; break; } if (covered) { add_multiple_row(M, w, v, -1); reiterate = true; } } } }
// **************************************************************************** // Calculates the inverse of N x N matrix A and stores it in matrix Ainv. // It is assumed that the memory required for this has already been allocated. // The data in matrix A is not destroyed, unless the same address is supplied for Ainv. // (This case should be successfully handled also.) // The function returns -1 if the matrix is not invertible. // **************************************************************************** int matrix_invert(double *A, double *Ainv, long int N) { double *backup = malloc_1d_array_double(N*N); double pivot, factor; long int pivot_row; if (A==NULL || Ainv==NULL || N<1) quit_error((char*)"Bad input data to matrix_invert"); // Backup the A matrix so that manipulations can be performed here // without damaging the original matrix. for (long int row=0; row<N; row++) for (long int col=0; col<N; col++) backup[row*N+col]=A[row*N+col]; // First, fill Ainv with the identity matrix for (long int row=0; row<N; row++) { for (long int col=0; col<N; col++) { if (row==col) Ainv[row*N+col]=1; else Ainv[row*N+col]=0; } } // Calculate the inverse using Gauss-Jordan elimination for (long int col=0; col<N; col++) { //display_augmented(backup, Ainv, N); pivot_row=-1; pivot=0.0; for (long int row=col; row<N; row++) { if (fabs(backup[row*N+col])>fabs(pivot)) { pivot_row=row; pivot=backup[row*N+col]; } } //printf("Pivot: %lf\n\n", pivot); if (pivot_row<0 || pivot_row>=N || fabs(pivot)<DBL_EPSILON) { free_1d_array_double(backup); return -1; } else { swap_row(col, pivot_row, backup, Ainv, N); multiply_row(col, 1.0/pivot, backup, Ainv, N); for (long int elim_row=0; elim_row<N; elim_row++) { if (elim_row!=col) { factor=-backup[elim_row*N+col]; add_multiple_row(factor, col, elim_row, backup, Ainv, N); } } } } free_1d_array_double(backup); return 0; }