public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { if (solverParametrs is LOSParametrs) { LOSParametrs LOSParametrs = solverParametrs as LOSParametrs; Vector x, r, z, p; double alpha, betta; int size, k; double Residual, pp, rightnorm; Vector Ax; Vector LAU, Ur; size = initialSolution.Size; x = new Vector(size); r = new Vector(size); z = new Vector(size); p = new Vector(size); Ax = new Vector(size); LAU = new Vector(size); Ur = new Vector(size); x = initialSolution; Ax = matrix.SourceMatrix.Multiply(x); r = matrix.SSolve(rightPart - Ax); z = matrix.QSolve(r); p = matrix.SSolve(matrix.SourceMatrix.Multiply(z)); rightnorm = matrix.SSolve(rightPart).Norm(); Residual = r.Norm() / rightnorm; solverLogger.AddIterationInfo(0, Residual); for (k = 1; k <= LOSParametrs.MaxIterations && Residual > LOSParametrs.Epsilon; k++) { pp = p * p; alpha = (p * r) / pp; x = x + z * alpha; r = r - p * alpha; Ur = matrix.QSolve(r); LAU = matrix.SourceMatrix.Multiply(Ur); LAU = matrix.SSolve(LAU); betta = -(p * LAU) / pp; z = Ur + z * betta; p = LAU + p * betta; Residual = r.Norm() / rightnorm; if (System.Double.IsInfinity(Residual)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by LOS."); return(x); } if (System.Double.IsNaN(Residual)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by LOS."); return(x); } solverLogger.AddIterationInfo(k, Residual); } return(x); } else { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GaussSeidel"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GaussSeidel"); } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { MSGParametrs ConGradParametrs = solverParametrs as MSGParametrs; if (ConGradParametrs == null) { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in MSG"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in MSG"); } else { //prestart int oIter = 0; double alpha, beta, oNev, bNev, scalRO, scaleRN; Vector x = initialSolution, rNew, rOld, z, ap, p; rOld = rightPart - matrix.SourceMatrix.Multiply(x); z = matrix.QSolve(matrix.SSolve(rOld)); p = z; ap = matrix.SourceMatrix.Multiply(p); bNev = rightPart.Norm(); oNev = rOld.Norm() / bNev; scalRO = z * rOld; // x = matrix.QSolve(x); solverLogger.AddIterationInfo(oIter, oNev);//logger if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by MSG."); return x; } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by MSG."); return x; } while (oIter < ConGradParametrs.MaxIterations && oNev > ConGradParametrs.Epsilon) { alpha = scalRO / (ap * p); x = x + p * alpha; //if (oIter % 100 == 0) //rNew = matrix.QMultiply(rightPart - matrix.SMultiply(matrix.SourceMatrix.Multiply(x))); //else rNew = rOld - ap * alpha; z = matrix.QSolve(matrix.SSolve(rNew)); scaleRN = z * rNew; beta = scaleRN / scalRO; scalRO = scaleRN; p = z + p * beta; ap = matrix.SourceMatrix.Multiply(p); rOld = rNew; oIter++; oNev = rNew.Norm() / bNev; if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by MSG."); return x; } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by MSG."); return x; } solverLogger.AddIterationInfo(oIter, oNev);//logger } return x; } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { GMRESParameters GMRESParameters = solverParametrs as GMRESParameters; if (GMRESParameters != null) { Vector[] V, H; Vector residual, x, d, z, w, tmp; bool continueCalculations; double epsilon = GMRESParameters.Epsilon; int m = GMRESParameters.M; int maxIterations = GMRESParameters.MaxIterations; int n = rightPart.Size; x = initialSolution; residual = rightPart - matrix.SourceMatrix.Multiply(x); residual = matrix.SSolve(residual); double rightPartNorm = matrix.SSolve(rightPart).Norm(); double residualNorm = residual.Norm(); if (System.Double.IsInfinity(residualNorm / rightPartNorm)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by GMRES."); return(x); } if (System.Double.IsNaN(residualNorm / rightPartNorm)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by GMRES."); return(x); } x = matrix.QMultiply(initialSolution); V = new Vector[m]; for (int i = 0; i < m; i++) { V[i] = new Vector(n); } H = new Vector[m]; for (int i = 0; i < m; i++) { H[i] = new Vector(m + 1); } d = new Vector(m + 1); for (int k = 1; k <= maxIterations && residualNorm / rightPartNorm > epsilon; k++) { d.Nullify(); V[0] = residual * (1.0 / residualNorm); continueCalculations = true; for (int j = 1; j <= m && continueCalculations; j++) { tmp = matrix.QSolve(V[j - 1]); w = matrix.SSolve(matrix.SourceMatrix.Multiply(tmp)); for (int l = 1; l <= j; l++) { H[j - 1][l - 1] = V[l - 1] * w; w = w - V[l - 1] * H[j - 1][l - 1]; } H[j - 1][j] = w.Norm(); if (Math.Abs(H[j - 1][j]) < 1e-10) { m = j; continueCalculations = false; } else { if (j != m) { V[j] = w * (1.0 / H[j - 1][j]); } } } d[0] = residualNorm; z = solveMinSqrProblem(d, H, m); x = x + multiplyMatrixVector(z, V); tmp = rightPart - matrix.SourceMatrix.Multiply(matrix.QSolve(x)); residual = matrix.SSolve(tmp); residualNorm = residual.Norm(); if (System.Double.IsInfinity(residualNorm / rightPartNorm)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by GMRES."); return(x); } if (System.Double.IsNaN(residualNorm / rightPartNorm)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by GMRES."); return(x); } solverLogger.AddIterationInfo(k, residualNorm / rightPartNorm); } return(matrix.QSolve(x)); } else { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GMRES"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GMRES"); } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { BCGStabParametrs ConGradParametrs = solverParametrs as BCGStabParametrs; if (ConGradParametrs == null) { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in BSGStab"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in BSGSTab"); } else { int oIter = 0; double nPi, oPi, alpha, w, oNev, bNev, betta; oPi = alpha = w = 1; int size = rightPart.Size; Vector x, r, rTab, s, t, z, sqt, y; Vector v = new Vector(size); Vector p = new Vector(size); v.Nullify(); p.Nullify(); x = initialSolution; r = rightPart - matrix.SourceMatrix.Multiply(x); rTab = r; bNev = rightPart.Norm(); oNev = r.Norm() / bNev; solverLogger.AddIterationInfo(oIter, oNev);//logger if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by BSG Stab."); return(x); } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by BSG Stab."); return(x); } while (oIter < ConGradParametrs.MaxIterations && oNev > ConGradParametrs.Epsilon) { nPi = rTab * r; betta = (nPi / oPi) * (alpha / w); p = r + (p - v * w) * betta; y = matrix.QSolve(matrix.SSolve(p)); v = matrix.SourceMatrix.Multiply(y); alpha = nPi / (rTab * v); x = x + y * alpha;//УТОЧНИТЬ!!!!!!!!!!!!!!! s = r - v * alpha; if (s.Norm() / bNev < ConGradParametrs.Epsilon) { return(x); } z = matrix.QSolve(matrix.SSolve(s)); t = matrix.SourceMatrix.Multiply(z); sqt = matrix.QSolve(matrix.SSolve(t)); w = (z * sqt) / (sqt * sqt); x = x + z * w;//УТОЧНИТЬ!!!!!!!!!!!!!!!!!!! r = s - t * w; oPi = nPi; oIter++; oNev = r.Norm() / bNev; if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by BSG Stab."); return(x); } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by BSG Stab."); return(x); } solverLogger.AddIterationInfo(oIter, oNev);//logger } return(x); } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { GMRESParameters GMRESParameters = solverParametrs as GMRESParameters; if (GMRESParameters != null) { Vector[] V, H; Vector residual, x, d, z, w, tmp; bool continueCalculations; double epsilon = GMRESParameters.Epsilon; int m = GMRESParameters.M; int maxIterations = GMRESParameters.MaxIterations; int n = rightPart.Size; x = initialSolution; residual = rightPart - matrix.SourceMatrix.Multiply(x); residual = matrix.SSolve(residual); double rightPartNorm = matrix.SSolve(rightPart).Norm(); double residualNorm = residual.Norm(); if (System.Double.IsInfinity(residualNorm / rightPartNorm)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by GMRES."); return x; } if (System.Double.IsNaN(residualNorm / rightPartNorm)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by GMRES."); return x; } x = matrix.QMultiply(initialSolution); V = new Vector[m]; for (int i = 0; i < m; i++) V[i] = new Vector(n); H = new Vector[m]; for (int i = 0; i < m; i++) H[i] = new Vector(m + 1); d = new Vector(m + 1); for (int k = 1; k <= maxIterations && residualNorm / rightPartNorm > epsilon; k++) { d.Nullify(); V[0] = residual * (1.0 / residualNorm); continueCalculations = true; for (int j = 1; j <= m && continueCalculations; j++) { tmp = matrix.QSolve(V[j - 1]); w = matrix.SSolve(matrix.SourceMatrix.Multiply(tmp)); for (int l = 1; l <= j; l++) { H[j - 1][l - 1] = V[l - 1] * w; w = w - V[l - 1] * H[j - 1][l - 1]; } H[j - 1][j] = w.Norm(); if (Math.Abs(H[j - 1][j]) < 1e-10) { m = j; continueCalculations = false; } else { if(j != m) V[j] = w * (1.0 / H[j - 1][j]); } } d[0] = residualNorm; z = solveMinSqrProblem(d, H, m); x = x + multiplyMatrixVector(z, V); tmp = rightPart - matrix.SourceMatrix.Multiply(matrix.QSolve(x)); residual = matrix.SSolve(tmp); residualNorm = residual.Norm(); if (System.Double.IsInfinity(residualNorm / rightPartNorm)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by GMRES."); return x; } if (System.Double.IsNaN(residualNorm / rightPartNorm)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by GMRES."); return x; } solverLogger.AddIterationInfo(k, residualNorm / rightPartNorm); } return matrix.QSolve(x); } else { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GMRES"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GMRES"); } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { BCGStabParametrs ConGradParametrs = solverParametrs as BCGStabParametrs; if (ConGradParametrs == null) { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in BSGStab"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in BSGSTab"); } else { int oIter = 0; double nPi, oPi, alpha, w, oNev, bNev, betta; oPi = alpha = w = 1; int size = rightPart.Size; Vector x, r, rTab, s, t, z, sqt, y; Vector v = new Vector(size); Vector p = new Vector(size); v.Nullify(); p.Nullify(); x = initialSolution; r = rightPart - matrix.SourceMatrix.Multiply(x); rTab = r; bNev = rightPart.Norm(); oNev = r.Norm() / bNev; solverLogger.AddIterationInfo(oIter, oNev);//logger if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by BSG Stab."); return x; } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by BSG Stab."); return x; } while (oIter < ConGradParametrs.MaxIterations && oNev > ConGradParametrs.Epsilon) { nPi = rTab * r; betta = (nPi / oPi) * (alpha / w); p = r + (p - v * w) * betta; y= matrix.QSolve(matrix.SSolve(p)); v = matrix.SourceMatrix.Multiply(y); alpha = nPi / (rTab * v); x = x + y * alpha;//УТОЧНИТЬ!!!!!!!!!!!!!!! s = r - v * alpha; if (s.Norm() / bNev < ConGradParametrs.Epsilon) return x; z = matrix.QSolve(matrix.SSolve(s)); t = matrix.SourceMatrix.Multiply(z); sqt = matrix.QSolve(matrix.SSolve(t)); w = (z * sqt) / (sqt * sqt); x = x + z * w;//УТОЧНИТЬ!!!!!!!!!!!!!!!!!!! r = s - t * w; oPi = nPi; oIter++; oNev = r.Norm() / bNev; if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by BSG Stab."); return x; } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by BSG Stab."); return x; } solverLogger.AddIterationInfo(oIter, oNev);//logger } return x; } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { if (solverParametrs is LOSParametrs) { LOSParametrs LOSParametrs = solverParametrs as LOSParametrs; Vector x, r, z, p; double alpha, betta; int size, k; double Residual,pp,rightnorm; Vector Ax; Vector LAU, Ur; size = initialSolution.Size; x = new Vector(size); r = new Vector(size); z = new Vector(size); p = new Vector(size); Ax = new Vector(size); LAU = new Vector(size); Ur = new Vector(size); x = initialSolution; Ax = matrix.SourceMatrix.Multiply(x); r = matrix.SSolve(rightPart - Ax); z = matrix.QSolve(r); p = matrix.SSolve(matrix.SourceMatrix.Multiply(z)); rightnorm = matrix.SSolve(rightPart).Norm(); Residual = r.Norm()/rightnorm; solverLogger.AddIterationInfo(0, Residual); for (k = 1; k <= LOSParametrs.MaxIterations && Residual > LOSParametrs.Epsilon; k++) { pp = p*p; alpha = (p * r) / pp; x = x + z * alpha; r = r - p * alpha; Ur = matrix.QSolve(r); LAU = matrix.SourceMatrix.Multiply(Ur); LAU = matrix.SSolve(LAU); betta = - (p * LAU) / pp; z = Ur + z * betta; p = LAU + p * betta; Residual = r.Norm() / rightnorm; if (System.Double.IsInfinity(Residual)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by LOS."); return x; } if (System.Double.IsNaN(Residual)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by LOS."); return x; } solverLogger.AddIterationInfo(k, Residual); } return x; } else { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GaussSeidel"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in GaussSeidel"); } }
public override Vector Solve(IPreconditioner matrix, Vector rightPart, Vector initialSolution, ILogger logger, ISolverLogger solverLogger, ISolverParametrs solverParametrs) { MSGParametrs ConGradParametrs = solverParametrs as MSGParametrs; if (ConGradParametrs == null) { logger.Error("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in MSG"); throw new Exception("Incorrect " + solverParametrs.GetType().Name.ToString() + " as a SolverParametrs in MSG"); } else { //prestart int oIter = 0; double alpha, beta, oNev, bNev, scalRO, scaleRN; Vector x = initialSolution, rNew, rOld, z, ap, p; rOld = rightPart - matrix.SourceMatrix.Multiply(x); z = matrix.QSolve(matrix.SSolve(rOld)); p = z; ap = matrix.SourceMatrix.Multiply(p); bNev = rightPart.Norm(); oNev = rOld.Norm() / bNev; scalRO = z * rOld; // x = matrix.QSolve(x); solverLogger.AddIterationInfo(oIter, oNev);//logger if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by MSG."); return(x); } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by MSG."); return(x); } while (oIter < ConGradParametrs.MaxIterations && oNev > ConGradParametrs.Epsilon) { alpha = scalRO / (ap * p); x = x + p * alpha; //if (oIter % 100 == 0) //rNew = matrix.QMultiply(rightPart - matrix.SMultiply(matrix.SourceMatrix.Multiply(x))); //else rNew = rOld - ap * alpha; z = matrix.QSolve(matrix.SSolve(rNew)); scaleRN = z * rNew; beta = scaleRN / scalRO; scalRO = scaleRN; p = z + p * beta; ap = matrix.SourceMatrix.Multiply(p); rOld = rNew; oIter++; oNev = rNew.Norm() / bNev; if (System.Double.IsInfinity(oNev)) { logger.Error("Residual is infinity. It is impossible to solve this SLAE by MSG."); return(x); } if (System.Double.IsNaN(oNev)) { logger.Error("Residual is NaN. It is impossible to solve this SLAE by MSG."); return(x); } solverLogger.AddIterationInfo(oIter, oNev);//logger } return(x); } }