高斯消去法解线性方程组

解线性方程组,只支持有唯一解的情况。如果无解或者有多个解,则退出。

 

 

方程组的系数阵为m*m的方阵A,增广阵为m*n矩阵为B,有n=m+1。增广阵在系数阵加入的那1列就是方程组等号右边那些常数组成的列向量。

 

 

算法步骤:

1>. 先搞第1列。找出第1列中绝对值最大的数,称作主元素(mainElement)。把主元素所在的行与第1行进行行交换,则主元素此时落在对角线上。将第1行(所有元素)除以主元素,则主元素为1。

1>. 第1列的元素为a[u][0],其中u=1...m-1。第2行与第1行进行row addition,即r 2+(-a[u][0])*r1,这样第2行第1个元素会成为0。第3行以致第m行也进行r_u-a[u][0]*r1这样的操作,则在第1列,除了第1 行之外,所有下面的元素都变成0.

1>.对第2列重复上面的步骤,但注意主元素要放到对角线(左上-右下)上,进行row addition时,选择第2行。

1>.对列j重复第2列的操作,有2<=j<=m-2(系数阵最后一列和增广的那1列不用搞)。

1>.完成之后,则系数阵成为上三角阵。此时未知数x[m-1]首先得解。然后将x[m-1]回代到上一行,可以解得x[m-2];再将x[m-1], x[m-2]往上回代解得x[m-3] ... 直到解出x[0]。

1>.打完收工。

 

#! /usr/bin/env python #coding=utf-8 #[email protected] import math class LinEqu: def __init__(self, mat_aug): self.mat_aug = mat_aug; self.index = len(mat_aug[0])-1; self.solution = [0 for a in range(self.index)]; print 'Original matrix: '; self.printMatrix(); def eliminate(self): m = self.index; n = self.index+1; i,j=0,0; while True: if i>m-2 or j>n-2: break; print '/ni=%d, j=%d' % (i , j); mainElement = 0.0; for k in range(i+1, m): if math.fabs(mat_aug[k][i]>mainElement): mainElement=mat_aug[k][i]; exchangeRow = k; if not mainElement>0.0: print 'There is no solution or the solutions are more than 1. Exit.'; return None; for l in range(n): #Swap row i and exchangeRow that contains mainElement mat_aug[i][l], mat_aug[exchangeRow][l] = mat_aug[exchangeRow][l], mat_aug[i][l]; mat_aug[i][l] /= mainElement; print 'After round %d of row swap and normalization: ' % i; self.printMatrix(); for u in range(i+1, m): pivot = mat_aug[u][j]; for v in range(n): mat_aug[u][v]=mat_aug[u][v]-mat_aug[i][v]*pivot; print 'After round %d of elimination: ' % i; self.printMatrix(); i+=1; j+=1; def backSub(self): mat_aug = self.mat_aug; x=self.solution; m=self.index; n=self.index+1; b=[0 for row in range(self.index)]; x[m-1]=mat_aug[m-1][n-1]/mat_aug[m-1][n-2]; for i in reversed(range(self.index)): b[i] = self.mat_aug[i][n-1]; sum = 0.0; for j in reversed(range(i+1, n-1)): sum+=mat_aug[i][j]*x[j]; x[i] = (b[i]-sum)/mat_aug[i][i]; def printMatrix(self): for row in range(len(self.mat_aug)): print mat_aug[row]; print; def printSolu(self): print print 'The soluiton is: ', self.solution; def main(self): self.eliminate(); self.backSub(); self.printSolu(); if __name__=='__main__': #mat_aug = [[9.0,3,4,7],[4,3,4,8],[1,1,1,3]]; mat_aug = [[0.0,2.0,1.0,4.0],[1.0,1.0,2.0,6.0],[2.0,1.0,1.0,7]]; equation = LinEqu(mat_aug); equation.main();

 

 

解的过程:

$ ./gaussian_elimination.py
Original matrix:
[0.0, 2.0, 1.0, 4.0]
[1.0, 1.0, 2.0, 6.0]
[2.0, 1.0, 1.0, 7]


i=0, j=0
After round 0 of row swap and normalization:
[1.0, 0.5, 0.5, 3.5]
[1.0, 1.0, 2.0, 6.0]
[0.0, 2.0, 1.0, 4.0]

After round 0 of elimination:
[1.0, 0.5, 0.5, 3.5]
[0.0, 0.5, 1.5, 2.5]
[0.0, 2.0, 1.0, 4.0]


i=1, j=1
After round 1 of row swap and normalization:
[1.0, 0.5, 0.5, 3.5]
[0.0, 1.0, 0.5, 2.0]
[0.0, 0.5, 1.5, 2.5]

After round 1 of elimination:
[1.0, 0.5, 0.5, 3.5]
[0.0, 1.0, 0.5, 2.0]
[0.0, 0.0, 1.25, 1.5]


The soluiton is: [2.2000000000000002, 1.3999999999999999, 1.2]

 

 

参考资料:

1. [web] http://ceee.rice.edu/Books/CS/chapter2/linear43.html

2. [web]. Wikipedia contributors, "Gaussian elimination," Wikipedia, The Free Encyclopedia,http://en.wikipedia.org/w/index.php?title=Gaussian_elimination&oldid=392526152 (accessed November 28, 2010).

3. [web]. http://marekrychlik.com/cgi-bin/gauss.cgi

 

 

 

 

 

 

 

 

你可能感兴趣的:(高斯消去法解线性方程组)