protected override MsrMatrix ComputeMatrix() { MsrMatrix Src = m_Src.AssemblyMatrix; MsrMatrix Approx = new MsrMatrix(Src.RowPartitioning, Src.ColPartition); int i0 = Src.RowPartitioning.i0; int LocalLength = Src.RowPartitioning.LocalLength; double BDFfactor; switch (m_SolverConf.Control.Algorithm) { case SolutionAlgorithms.Steady_SIMPLE: BDFfactor = 0.0; break; case SolutionAlgorithms.Unsteady_SIMPLE: int BDFOrder = m_SolverConf.BDFOrder; double dt = m_SolverConf.dt; BDFfactor = m_BDF.beta[BDFOrder - 1][0] / (m_BDF.gamma[BDFOrder - 1] * dt); break; default: throw new ArgumentException(); } switch (m_SolverConf.Control.PredictorApproximation) { case PredictorApproximations.Identity: case PredictorApproximations.Identity_IP1: Approx.AccEyeSp(); Approx.AccEyeSp(BDFfactor); break; case PredictorApproximations.Diagonal: for (int row = 0; row < LocalLength; row++) { double Src_ii = Src[row + i0, row + i0]; double Rho_ii = m_Rho[row + i0, row + i0]; Approx[row + i0, row + i0] = BDFfactor * Rho_ii + Src_ii; } break; case PredictorApproximations.BlockDiagonal: BlockDiagonalMatrix SrcBlock = new BlockDiagonalMatrix(Src, Src.RowPartitioning.LocalLength / m_NoOfCells, Src.ColPartition.LocalLength / m_NoOfCells); Approx.Acc(1.0, SrcBlock); Approx.Acc(BDFfactor, m_Rho); break; default: throw new ArgumentException(); } return(Approx); }
protected override MsrMatrix DefineMatrix(double dt) { MsrMatrix res = new MsrMatrix(m_MatAsmblyLevelSet.AssemblyMatrix); if ((m_ModeRelaxLevelSet == RelaxationTypes.Implicit) && (m_RelaxFactor != 0.0)) { res.Acc(m_RelaxFactor, m_MatAsmblyLevelSetApprox.AssemblyMatrix); } if (m_BDF != null) { double LhsSummand = m_BDF.GetLhsSummand(dt, m_solverConf.BDFOrder); res.AccEyeSp(LhsSummand); } return(res); }
/// <summary> /// /// </summary> /// <param name="dt"></param> /// <returns></returns> protected override MsrMatrix DefineMatrix(double dt) { MsrMatrix res = new MsrMatrix(m_MatAsmblyPredictor[0].AssemblyMatrix); //See left-hand side of Eq. (18) in //B. Klein, F. Kummer, M. Keil, and M. Oberlack, //An extension of the SIMPLE based discontinuous Galerkin solver to unsteady incompressible flows, J. Comput. Phys., 2013. if (m_RelaxFactor != 0.0) { res.Acc(m_RelaxFactor, m_MatAsmblyPredictorApprox.AssemblyMatrix); } if (m_BDF != null) { double LhsSummand = m_BDF.GetLhsSummand(dt, base.m_solverConf.BDFOrder); res.AccEyeSp(LhsSummand); } return(res); }
public void ImplicitEuler(double dt, SubGrid S, SinglePhaseField inout_Levset) { var VolMsk = S.VolumeMask; var EdgMsk = S.InnerEdgesMask; UnsetteledCoordinateMapping Map = inout_Levset.Mapping; if (dt <= 0.0) { throw new ArgumentOutOfRangeException("Timestep size must be greater than 0."); } MsrMatrix Pmtx = PenaltyMatrix(EdgMsk, inout_Levset.Basis, inout_Levset.Basis); Pmtx.Scale(-1.0); int[] SubVecIdx = Map.GetSubvectorIndices(S, true, new int[] { 0 }); int L = SubVecIdx.Length; MsrMatrix SubMtx = new MsrMatrix(L, L); Pmtx.AccSubMatrixTo(1.0, SubMtx, SubVecIdx, default(int[]), SubVecIdx, default(int[])); SubMtx.AccEyeSp(1.0 / dt); double[] RHS = new double[L]; double[] SOL = new double[L]; RHS.AccV(1.0 / dt, inout_Levset.CoordinateVector, default(int[]), SubVecIdx); using (var solver = new PARDISOSolver()) { solver.DefineMatrix(SubMtx); solver.Solve(SOL, RHS); } inout_Levset.CoordinateVector.ClearEntries(SubVecIdx); inout_Levset.CoordinateVector.AccV(1.0, SOL, SubVecIdx, default(int[])); }