void PrecomputeDistanceMatrix2D(int W, int H, bool show = true) { int N = area_cnt; //////////////////////////////////////////////////////////// // step III-1. build matrix A for distance computation // [CAUTION] this is NEGATED matrix to use Cholesky decomp. //////////////////////////////////////////////////////////// var C_dist = new CoordinateStorage <double>(N, N, 5 * N); // banded matrix without exception for (int matid_this = 0; matid_this < N; matid_this++) { List <int> matid_neighbor; if (!MatrixNeighbors.TryGetValue(matid_this, out matid_neighbor)) { continue; } double A_diag = -1e-6; // small value to use Cholesky decomposition Action <int> CheckNeighbor = (id) => { int matid_next = matid_neighbor[id]; if (matid_next != -1) { A_diag += -1.0; C_dist.At(matid_this, matid_next, -1.0); } }; CheckNeighbor(0); CheckNeighbor(1); CheckNeighbor(2); CheckNeighbor(3); C_dist.At(matid_this, matid_this, -A_diag); } var A_dist = Converter.ToCompressedColumnStorage(C_dist) as SparseMatrix; //////////////////////////////////////////////////////////// // step III-2. build matrix A for heat diffusion //////////////////////////////////////////////////////////// #if USE_3RDPARTY solver_dist = new SuperLU(A_dist); var options = solver_dist.Options; options.SymmetricMode = true; solver_dist.Factorize(); #else solver_dist = SparseCholesky.Create(A_dist, ColumnOrdering.MinimumDegreeAtPlusA); #endif }
void PrecomputeHeatMatrix2D(double dt) { int N = area_cnt; //////////////////////////////////////////////////////////// // step I-1. build matrix A for heat diffusion //////////////////////////////////////////////////////////// var C_heat = new CoordinateStorage <double>(N, N, 5 * N); // banded matrix without exception for (int matid_this = 0; matid_this < N; matid_this++) { List <int> matid_neighbor; if (!MatrixNeighbors.TryGetValue(matid_this, out matid_neighbor)) { continue; } if (matid_neighbor[0] != -1) { C_heat.At(matid_this, matid_neighbor[0], -1.0 * dt); } if (matid_neighbor[1] != -1) { C_heat.At(matid_this, matid_neighbor[1], -1.0 * dt); } if (matid_neighbor[2] != -1) { C_heat.At(matid_this, matid_neighbor[2], -1.0 * dt); } if (matid_neighbor[3] != -1) { C_heat.At(matid_this, matid_neighbor[3], -1.0 * dt); } C_heat.At(matid_this, matid_this, 1.0 + 4.0 * dt); } var A_heat = Converter.ToCompressedColumnStorage(C_heat) as SparseMatrix; //////////////////////////////////////////////////////////// // step I-2. build matrix A for heat diffusion //////////////////////////////////////////////////////////// #if USE_3RDPARTY solver_heat = new SuperLU(A_heat); var options = solver_heat.Options; options.SymmetricMode = true; solver_heat.Factorize(); #else solver_heat = SparseCholesky.Create(A_heat, ColumnOrdering.MinimumDegreeAtPlusA); #endif }
protected override IDisposableSolver <Complex> CreateSolver(SparseMatrix matrix, bool symmetric) { var solver = new SuperLU(matrix); if (symmetric) { var options = solver.Options; options.SymmetricMode = true; options.ColumnOrderingMethod = OrderingMethod.MinimumDegreeAtPlusA; options.DiagonalPivotThreshold = 0.001; } return(solver); }