雅可比迭代法和高斯赛德尔迭代法参考了另一个博主写的,觉得写的很好,很清晰。(若侵权,立删)
链接如下:
https://blog.csdn.net/Huanyuaner/article/details/120983944
根据上面链接里雅可比和高斯的求解算法,模仿着写了超松弛迭代法的解法
代码如下:
w为松弛因子
最下面注释里的precision()函数就是博主博客里的Accuracy()判断精度的函数
//超松弛迭代法SOR如下:
void SOR() {
for (int i = 0; i < 4; i++)
{
for (int j = 0; j < 4; j++)
{
C[i][j] = -A[i][j]*w / A[i][i];
if (i == j)
C[i][j] = 1.0 - w;
}
for (int i = 0; i < 4; i++)
C[i][4] = b[i]*w / A[i][i];
}
double x1 = X0[0], x2 = X0[1], x3 = X0[2], x4 = X0[3];
int k = 0;
while (true)
{
for (int i = 0; i < 4; i++)
{
X[i] = C[i][0] * x1 + C[i][1] * x2 + C[i][2] * x3 + C[i][3] * x4 + C[i][4];
if (precision(x1, x2, x3, x4)) return;
x1 = X[0];
x2 = X[1];
x3 = X[2];
x4 = X[3];
}
k++;
cout << "第" << k << "次SOR迭代计算结果:" << endl;
output();
}
return;
}
//超松弛迭代法展示完毕,由SOR(),precision(),output()组成
声明:
代码段中的这个部分其实是参考博主:求迭代公式中的各项系数矩阵的函数,也就是该博主的Matrix()函数。只是将这一小部分合并在了一起。
仔细去读参考博主的代码,你会发现这三种迭代方法在编写代码时,大部分特别相似,但是有些部分:
在循环迭代的过程中
例如:如上图所示的这四个分句在函数中的位置的不一样的。
1.jacobi迭代中:这四个分句在for循环外,如图:
这和jacobi迭代数学公式相呼应:
如图所示,k+1次迭代等号右边全是k次迭代对应的x的值,所以在Jacobi迭代中,四个分句要在for循环外面
2.同理,对于高斯赛德尔迭代法:
如图所示 举个例子:
x2的第k+1次迭代式中,等号右边:x1使用的是K+1次迭代,但是当x的下标值大于2时,也就是x3使用的是x3的第k次迭代,不是k+1次。那在xn的k+1迭代式中,等号右边的x的下标都是小于n的,所以使用的全是k+1次迭代。 那对应代码中:
这四个分句在for循环中。这样就能实时更新前一个已经迭代过的元素。
3.超松弛迭代法:
与高斯赛德尔迭代法很相似,就是加入了松弛因子w。
当时笔记是例题,但是不难看出:在jacobi和高斯迭代公式中:如果i=j,那迭代对应的系数矩阵中的系数为0,但是超松弛对应系数为:1-w,w为松弛因子;与高斯赛德尔迭代法相同的是:超松弛迭代法x的迭代系数什么时候是k+1,什么时候是k,与高斯赛德尔相同。所以四个分句同样也在for循环中。
除了四个分句的位置不同,还有精度函数调用位置也有相应变化,理解了四个分句位置的意义,其他也不难理解。