static public Pair <Vector, int> Modified_withSLAU(Vector vectorStart, ScalarFunk1_N[][] matrixFunks, ScalarFunk1_N[] vectorFunks, Stopwatch stopWatch, int iterExit = Int32.MaxValue, double EpsSwitch = 10e-6, double Eps = 10e-6) { //Итерации вида: J * deltaX = -F; Матрица J инициализируется единожды stopWatch.Start(); //Приближения var vectorX_next = new Vector(vectorFunks.Length); vectorX_next.Copy(vectorStart); var vectorX_current = new Vector(vectorFunks.Length); //Прибавка var deltaX = new Vector(vectorFunks.Length); var vectorF = new Vector(vectorFunks.Length); //Инициализация матрицы J var matrixJ = new Matrix(matrixFunks.Length); matrixJ.SetValueByFunks(matrixFunks, vectorX_next.data); //LUP разложение матрицы J var matrixJ_L = new Matrix(matrixJ.N); var matrixJ_U = new Matrix(matrixJ.N); var matrixJ_P = new Matrix(matrixJ.N); LUP_decomposition.LUP(matrixJ, matrixJ_L, matrixJ_U, matrixJ_P); var countIter = 0; do { //Счётчик итераций countIter++; vectorX_current.Copy(vectorX_next); //Инициализация вектора F новым приближением vectorF.SetValueByFunks(vectorFunks, vectorX_current.data); //Вычисление deltaX решением СЛАУ через LUP разложение deltaX = LUP_decomposition.SLAU(matrixJ_L, matrixJ_U, matrixJ_P, -1 * vectorF); //Получаем следующие приближение vectorX_next = vectorX_current + deltaX; //Вывод значений следующего приближения в консоль stopWatch.Stop(); //Console.Write($"#{countIter} Next vector: "); //vectorX_next.Show(); stopWatch.Start(); } while (deltaX.Norm() >= Eps && (deltaX.Norm() >= EpsSwitch && countIter < iterExit)); stopWatch.Stop(); return(new Pair <Vector, int> { FirstElement = vectorX_next, SecondElement = countIter }); }
static void Task_2() { var matrix = new Matrix(7); matrix.GenByDiagonalPred(3); Console.WriteLine("Generate matrix:"); matrix.Show(); Console.WriteLine("Generate vectorB:"); var vectorB = new Vector(matrix.N); vectorB.Generate(); vectorB.Show(); Console.WriteLine("\nMethod LU_________________________________"); var matrixL = new Matrix(matrix.N); var matrixU = new Matrix(matrix.N); var matrixP = new Matrix(matrix.N); LUP_decomposition.LUP(matrix, matrixL, matrixU, matrixP); Console.WriteLine("Result vector:"); var vectorLU = LUP_decomposition.SLAU(matrixL, matrixU, matrixP, vectorB); vectorLU.Show(); Console.WriteLine("\nGenerate begin VectorX:"); var beginVectorX = new Vector(matrix.N); beginVectorX.Generate(); beginVectorX.Show(); Console.WriteLine("Method Yacoby_________________________________"); var vectorYacoby = IterationMethods_SLAU.SLAU(matrix, vectorB, beginVectorX, IterationMethods_SLAU.Method.Yacoby); Console.Write("Result vector: "); vectorYacoby.Show(); Console.Write("Vector LU: "); vectorLU.Show(); Console.Write("Check with LU: "); (vectorYacoby - vectorLU).Show(); Console.WriteLine("Method Zeydel_________________________________"); var vectorZeydel = IterationMethods_SLAU.SLAU(matrix, vectorB, beginVectorX, IterationMethods_SLAU.Method.Zeydel); Console.Write("Result vector: "); vectorZeydel.Show(); Console.Write("Vector LU: "); vectorLU.Show(); Console.Write("Check with LU: "); (vectorZeydel - vectorLU).Show(); }
static public double AnalysisMethod(TypeKF typeKF, ScalarFunk1 f, double defA, double a, double b, double alpha, int n, double Eps) { double L = 2; Vector vectorH = new Vector(3); vectorH.data[1] = b - a; vectorH.data[2] = (b - a) / L; int countIter = 1; double result = 0.0; double tempR = Double.PositiveInfinity; do { countIter++; vectorH.data[0] = vectorH.data[1]; vectorH.data[1] = vectorH.data[2]; vectorH.data[2] = vectorH.data[1] / L; //Эйткен Vector vectorS = new Vector(3); vectorS.data[0] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[0]); vectorS.data[1] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[1]); vectorS.data[2] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[2]); double m = -Math.Log((Math.Abs(vectorS.data[2] - vectorS.data[1])) / (Math.Abs(vectorS.data[1] - vectorS.data[0]))) / Math.Log(L); //Рижардсон Matrix matrix_Cs_J = new Matrix(3); for (int i = 0; i < matrix_Cs_J.N; i++) { for (int j = 0; j < matrix_Cs_J.N - 1; j++) { matrix_Cs_J.data[i][j] = Math.Pow(vectorH.data[i], m + j); } matrix_Cs_J.data[i][matrix_Cs_J.N - 1] = -1; } Matrix matrix_Cs_J_L = new Matrix(n); Matrix matrix_Cs_J_U = new Matrix(n); Matrix matrix_Cs_J_P = new Matrix(n); LUP_decomposition.LUP(matrix_Cs_J, matrix_Cs_J_L, matrix_Cs_J_U, matrix_Cs_J_P); Vector vector_Cs_J = LUP_decomposition.SLAU(matrix_Cs_J_L, matrix_Cs_J_U, matrix_Cs_J_P, -1 * vectorS); result = vector_Cs_J.data[2]; tempR = vectorS.data[2] - result; } while (Math.Abs(tempR) > Eps); Console.WriteLine($"Count iter: {Math.Pow(L, countIter)}"); return(result); }
static public Vector Modified_withReverse(ScalarFunk1_N[][] matrixFunks, ScalarFunk1_N[] vectorFunks, double Eps = 10e-5) { Console.Write("Begin vector: "); var vectorX_next = new Vector(vectorFunks.Length); vectorX_next.SetValues(new double[] { 0.5, 0.5, 1.5, -1.0, -0.5, 1.5, 0.5, -0.5, 1.5, -1.5 }); vectorX_next.Show(); Console.WriteLine("Fill matrix: "); var matrixJ = new Matrix(matrixFunks.Length); matrixJ.SetValueByFunks(matrixFunks, vectorX_next.data); matrixJ.Show(); Console.WriteLine("Reverse matrix with LU: "); var matrixJ_L = new Matrix(matrixJ.N); var matrixJ_U = new Matrix(matrixJ.N); var matrixJ_P = new Matrix(matrixJ.N); LUP_decomposition.LUP(matrixJ, matrixJ_L, matrixJ_U, matrixJ_P); var matrixJ_reverse = LUP_decomposition.Reverse(matrixJ_L, matrixJ_U, matrixJ_P); matrixJ_reverse.Show(); var vectorF = new Vector(vectorFunks.Length); var vectorX_current = new Vector(vectorFunks.Length); var countIter = 0; do { countIter++; vectorX_current.Copy(vectorX_next); vectorF.SetValueByFunks(vectorFunks, vectorX_current.data); vectorX_next = vectorX_current - matrixJ_reverse * vectorF; Console.Write("Next vector: "); vectorX_next.Show(); } while ((vectorX_next - vectorX_current).Norm() >= Eps); Console.Write("Count iter: " + countIter.ToString() + '\n'); return(vectorX_next); }
static public double IKF_NewtonCots(ScalarFunk1 f, double defA, double a, double b, double alpha, int n) { //Получаем вектор узлов Vector vectorX = new Vector(n); double step = (b - a) / (n - 1); for (int i = 0; i < n; i++) { vectorX.data[i] = a + i * step; } //Вычисляем моменты от 0 до n - 1 Vector vectorMoments = new Vector(n); for (int i = 0; i < n; i++) { vectorMoments.data[i] = CountMoment(defA, a, b, alpha, i); } //Решаем СЛАУ и находим Aj Matrix matrixX = new Matrix(n); FillMatrixX(matrixX, vectorX); Matrix matrixX_L = new Matrix(n); Matrix matrixX_U = new Matrix(n); Matrix matrixX_P = new Matrix(n); LUP_decomposition.LUP(matrixX, matrixX_L, matrixX_U, matrixX_P); Vector vectorA = LUP_decomposition.SLAU(matrixX_L, matrixX_U, matrixX_P, vectorMoments); //Получем ответ по КФ double result = 0.0; for (int i = 0; i < n; i++) { result += vectorA.data[i] * f(vectorX.data[i]); } return(result); }
static void Task_1() { using (StreamReader reader = new StreamReader("InputMatrixs.txt")) { var strLine = ""; while (!reader.EndOfStream) { Console.Write("______________________________________\n"); #region Считывание матрицы strLine = reader.ReadLine(); if (strLine == "") { break; } var sizeMatrix = Int32.Parse(strLine); var matrixA = new Matrix(sizeMatrix); for (int i = 0; i < sizeMatrix; i++) { strLine = reader.ReadLine(); var values = strLine.Split(' '); for (int j = 0; j < sizeMatrix; j++) { matrixA.data[i][j] = Int32.Parse(values[j]); } } #endregion #region LU разложение var matrixL = new Matrix(sizeMatrix); var matrixU = new Matrix(sizeMatrix); var matrixP = new Matrix(sizeMatrix); LUP_decomposition.LUP(matrixA, matrixL, matrixU, matrixP); Console.Write('\n'); Console.Write("Matrix L\n"); matrixL.Show(); Console.Write('\n'); Console.Write("Matrix U\n"); matrixU.Show(); Console.Write('\n'); Console.Write("Matrix P\n"); matrixP.Show(); Console.Write('\n'); var checkMatrixLeft = matrixL * matrixU; Console.Write("Matrix L * U\n"); checkMatrixLeft.Show(); Console.Write('\n'); var checkMatrixRigth = matrixP * matrixA; Console.Write("Matrix P * A\n"); checkMatrixRigth.Show(); #endregion #region Определитель Console.Write('\n'); var detA = LUP_decomposition.Det(matrixL, matrixU, matrixP); Console.Write("Det A with LU: " + detA.ToString() + '\n'); #endregion #region Обратная матрица Console.Write('\n'); var A_reverse = LUP_decomposition.Reverse(matrixL, matrixU, matrixP); Console.Write("A_reverse with LU:\n"); A_reverse.Show(); Console.Write('\n'); var CheckReverse_1 = matrixA * A_reverse; Console.Write("Check Reverse (A * A_reverse):\n"); CheckReverse_1.Show(); Console.Write('\n'); var CheckReverse_2 = A_reverse * matrixA; Console.Write("Check Reverse (A_reverse * A):\n"); CheckReverse_2.Show(); #endregion #region СЛАУ Console.Write('\n'); Console.Write("SLAU with LU:\n"); Random rnd = new Random(); Vector b = new Vector(matrixA.N); Console.Write("Generate vector b: "); for (int i = 0; i < b.data.Length; i++) { b.data[i] = rnd.Next() % 100; Console.Write(b.data[i].ToString("0.00") + ' '); } Console.Write("\nResult x: "); var x = LUP_decomposition.SLAU(matrixL, matrixU, matrixP, b); for (int i = 0; i < x.data.Length; i++) { Console.Write(x.data[i].ToString("0.00") + ' '); } Console.Write('\n'); #endregion #region Число обусловленности Console.Write('\n'); Console.Write("Condition number: "); var condNumber = matrixA.Norm() * LUP_decomposition.Reverse(matrixL, matrixU, matrixP).Norm(); Console.Write(condNumber.ToString("0.00") + '\n'); #endregion } } }
static public double KF_Gauss(ScalarFunk1 f, double defA, double a, double b, double alpha, int n) { //Вычисляем моменты от 0 до 2n - 1 Vector vectorMoments = new Vector(2 * n); for (int i = 0; i < 2 * n; i++) { vectorMoments.data[i] = CountMoment(defA, a, b, alpha, i); } //Находим коеффициенты для W(x) Matrix matrixCoeff = new Matrix(n); FillMatrixCoeff(matrixCoeff, vectorMoments); Matrix matrixCoeff_L = new Matrix(n); Matrix matrixCoeff_U = new Matrix(n); Matrix matrixCoeff_P = new Matrix(n); LUP_decomposition.LUP(matrixCoeff, matrixCoeff_L, matrixCoeff_U, matrixCoeff_P); Vector vectorB_coeff = new Vector(n); for (int i = 0; i < n; i++) { vectorB_coeff.data[i] = -vectorMoments.data[n + i]; } Vector vectorCoeff = LUP_decomposition.SLAU(matrixCoeff_L, matrixCoeff_U, matrixCoeff_P, vectorB_coeff); //Находим узлы из W(x) Vector vectorX = new Vector(n); ScalarFunk1 funkW = (double X) => { double resultFunc = 0.0; for (int i = 0; i <= n; i++) { resultFunc += (i != n) ? vectorCoeff.data[i] * Math.Pow(X, i) : Math.Pow(X, n); } return(resultFunc); }; ScalarFunk1 funkW_Derivative = (double X) => { double resultFuncDerivative = 0.0; for (int i = 0; i <= n; i++) { resultFuncDerivative += (i != n) ? vectorCoeff.data[i] * Math.Pow(X, i - 1) * i : Math.Pow(X, n - 1) * n; } return(resultFuncDerivative); }; var resultCount = MethodNewton_Scalar.DefualtMethod(a, b, funkW, funkW_Derivative); vectorX.SetValues(resultCount.FirstElement); //Решаем СЛАУ и находим Aj Matrix matrixX = new Matrix(n); FillMatrixX(matrixX, vectorX); Matrix matrixX_L = new Matrix(n); Matrix matrixX_U = new Matrix(n); Matrix matrixX_P = new Matrix(n); LUP_decomposition.LUP(matrixX, matrixX_L, matrixX_U, matrixX_P); Vector vectorB_X = new Vector(n); for (int i = 0; i < n; i++) { vectorB_X.data[i] = vectorMoments.data[i]; } Vector vectorA = LUP_decomposition.SLAU(matrixX_L, matrixX_U, matrixX_P, vectorB_X); //Получем ответ по КФ double result = 0.0; for (int i = 0; i < n; i++) { result += vectorA.data[i] * f(vectorX.data[i]); } return(result); }
static public double AnalysisMethod_Opt(TypeKF typeKF, ScalarFunk1 f, double defA, double a, double b, double alpha, int n, double Eps) { double L = 2; Vector vectorH = new Vector(3); vectorH.data[0] = b - a; vectorH.data[1] = vectorH.data[0] / L; vectorH.data[2] = vectorH.data[1] / L; //Эйткен Vector vectorS = new Vector(3); vectorS.data[0] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[0]); vectorS.data[1] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[1]); vectorS.data[2] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[2]); double m = -Math.Log((vectorS.data[2] - vectorS.data[1]) / (vectorS.data[1] - vectorS.data[0])) / Math.Log(L); double R = (vectorS.data[2] - vectorS.data[1]) / (Math.Pow(L, m) - 1); double h_opt = vectorH.data[2] * Math.Pow(Eps / Math.Abs(R), 1.0 / m); //Чтобы укладывался в отрезок [a, b] int k = (Int32)Math.Ceiling((b - a) / h_opt); Console.WriteLine($"Count opt: {k}"); //double logK = Math.Log(k) / Math.Log(L); //logK = Math.Ceiling(logK); //k = (int)Math.Pow(L, logK); vectorH.data[1] = ((b - a) / k) * L * L; vectorH.data[2] = ((b - a) / k) * L; if (vectorH.data[1] > (b - a) || vectorH.data[2] > (b - a)) { Console.WriteLine($"Count iter: {Math.Pow(L, 3)}"); return(vectorS.data[2]); } else { int countIter = (int)k; double result = 0.0; double tempR = Double.PositiveInfinity; do { countIter *= (int)L; vectorH.data[0] = vectorH.data[1]; vectorH.data[1] = vectorH.data[2]; vectorH.data[2] = vectorH.data[1] / L; //Эйткен vectorS.data[0] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[0]); vectorS.data[1] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[1]); vectorS.data[2] = SKF(typeKF, f, defA, a, b, alpha, n, vectorH.data[2]); m = -Math.Log((Math.Abs(vectorS.data[2] - vectorS.data[1])) / (Math.Abs(vectorS.data[1] - vectorS.data[0]))) / Math.Log(L); //Ричардсон Matrix matrix_Cs_J = new Matrix(3); for (int i = 0; i < matrix_Cs_J.N; i++) { for (int j = 0; j < matrix_Cs_J.N - 1; j++) { matrix_Cs_J.data[i][j] = Math.Pow(vectorH.data[i], m + j); } matrix_Cs_J.data[i][matrix_Cs_J.N - 1] = -1; } Matrix matrix_Cs_J_L = new Matrix(n); Matrix matrix_Cs_J_U = new Matrix(n); Matrix matrix_Cs_J_P = new Matrix(n); LUP_decomposition.LUP(matrix_Cs_J, matrix_Cs_J_L, matrix_Cs_J_U, matrix_Cs_J_P); Vector vector_Cs_J = LUP_decomposition.SLAU(matrix_Cs_J_L, matrix_Cs_J_U, matrix_Cs_J_P, -1 * vectorS); result = vector_Cs_J.data[2]; tempR = vectorS.data[2] - result; } while (Math.Abs(tempR) > Eps); Console.WriteLine($"Count iter: {countIter}"); return(result); } }