高斯消元法求解方程组


    • 引子
      • 高斯消元法简介
      • 引例
    • 求解过程
    • 编程实现高斯消元法C

1. 引子

1. 高斯消元法简介

数学上,高斯消元法(Gaussian Elimination),是线性代数规划中的一个算法,可用来为线性方程组求解。

2. 引例

求解如下方程组:

2x+3y+z=4x2y+4z=53x+8y2z=13

2. 求解过程

可以将方程组和矩阵联系起来。如下:

2x+3y+z=11x2y+3z=63x+8y2z=13(1)(2)(3)

21332813211613(广)

(1)2(2)33(2) 得:

x2y+3z=67y5z=114y11z=5(4)(5)(6)

10027143511615

(6)2(7) 得:

x2y+3z=67y5z=1z=3(7)(8)(9)

100270351613()

还可以进一步简化:

x2y+3z=6y57z=17z=3(7)(8)(9)

10021035716173()

(7)+2(8)(8)+57(9) 继续进行化简:

x=1y=2z=3(7)(8)(9)

100010001123()

可见,当增广矩阵简化为标准形后,解即为矩阵最后一列的值。因此,我们可以脱离原方程组,对矩阵进行化简,得到方程组的解。

3. 编程实现高斯消元法(C#)

    using System.Collections.Generic;
    using System.Linq;

    namespace GaussianEliminationLib
    {
        public static class GaussianElimination
        {
            public static List<double> Resolve(IEnumerabledouble>> equationSet)
            {
                // 存储方程组矩阵
                Listdouble>> equationSetList = new Listdouble>>();
                foreach(IEnumerable<double> equation in equationSet)
                {
                    equationSetList.Add(equation.ToList());
                }

                for (int i = 0; i < equationSetList.Count; ++i)
                {
                    // 化简成行最简形
                    Simplitify(equationSetList, i, i);
                }
                // 化简成标准形
                return SimplitifyAgain(equationSetList);
            }

            private static void Simplitify(Listdouble>> equationSet, int rowStart, int colStart)
            {
                // 选择当前列最大行
                int pivotRow = FindPivotRow(equationSet, rowStart, colStart);
                SwapRows(equationSet, rowStart, pivotRow);

                int cols = equationSet[rowStart].Count;
                double maxValue = equationSet[rowStart][colStart];
                for (int i = rowStart; i < equationSet.Count; ++i)
                {
                    for (int j = colStart; j < cols; ++j)
                    {
                        equationSet[i][j] /= maxValue;
                    }
                }

                for (int i = rowStart + 1; i < equationSet.Count; ++i)
                {
                    double primer = equationSet[i][colStart];
                    for (int j = colStart; j < cols; ++j)
                    {
                        equationSet[i][j] -= primer * equationSet[rowStart][j];
                    }
                }
            }

            private static List<double> SimplitifyAgain(Listdouble>> equationSet)
            {
                int solutionsCount = equationSet.Count;
                List<double> solutions = new List<double>(solutionsCount);
                for (int i = 0; i < equationSet.Count; ++i)
                {
                    solutions.Add(0.0);
                }

                for (int i = equationSet.Count - 1; i >= 0; --i)
                {
                    double value = 0.0;
                    for (int j = 0; j < solutionsCount; ++j)
                    {
                        value += solutions[j] * equationSet[i][j];
                    }
                    solutions[i] = equationSet[i][equationSet.Count] - value;
                }

                return solutions;
            }

            private static int FindPivotRow(Listdouble>> equationSet, int rowStart, int col)
            {
                int row = rowStart;
                double value = equationSet[rowStart][col];
                for (int i = rowStart; i < equationSet.Count(); ++i)
                {
                    if (value < equationSet[i][col])
                    {
                        row = i;
                        value = equationSet[i][col];
                    }
                }
                return row;
            }   

            private static void SwapRows(Listdouble>> equationSet, int currentRow, int pivotRow)
            {
                List<double> row = equationSet[currentRow];
                equationSet[currentRow] = equationSet[pivotRow];
                equationSet[pivotRow] = row;
            }
        }
    }

你可能感兴趣的:(数学,学习笔记)