东北大学数值分析上机实验报告.docx
《东北大学数值分析上机实验报告.docx》由会员分享,可在线阅读,更多相关《东北大学数值分析上机实验报告.docx(21页珍藏版)》请在冰豆网上搜索。
东北大学数值分析上机实验报告
《数值分析》上机实验报告
课题三解线性方程组的迭代法
学生姓名:
学生系别:
学生班级:
日期:
上机实践报告
【运行环境】
软件:
Windows、MicrosoftVisualC++6.0
PC一台
【问题提出】
对课题二所列目的和意义的线性方程组,试分别选用Jacobi迭代法,Gauss-Seidol迭代法和SOR方法计算其解。
【实践要求】
1、体会迭代法求解线性方程组,并能与消去法做比较;
2、分别对不同精度要求,如ε=10-3,10-4,10-5由迭代次数体会该迭代法的收敛快慢;
3、对方程组2,3使用SOR方法时,选取松弛因子=0.8,0.9,1,1.1,1.2等,试看对算法收敛性的影响,并能找出你所选用的松弛因子的最佳者;
4、给出各种算法的设计程序和计算结果。
【目的意义】
1、通过上机计算体会迭代法求解线性方程组的特点,并能和消去法比较;
2、运用所学的迭代法算法,解决各类线性方程组,编出算法程序;
3、体会上机计算时,终止步骤<或k>(予给的迭代次数),对迭代法敛散性的意义;
4、体会初始解x,松弛因子的选取,对计算结果的影响。
【程序代码】
//Jacobi.cpp
#include
#include
usingnamespacestd;
#defineN15//最大迭代次数
#defineP10//矩阵的阶数
//#defineP8
staticdoublea[10][10]={4,2,-3,-1,2,1,0,0,0,0,
8,6,-5,-3,6,5,0,1,0,0,
4,2,-2,-1,3,2,-1,0,3,1,
0,-2,1,5,-1,3,-1,1,9,4,
-4,2,6,-1,6,7,-3,3,2,3,
8,6,-8,5,7,17,2,6,-3,5,
0,2,-1,3,-4,2,5,3,0,1,
16,10,-11,-9,17,34,2,-1,2,2,
4,6,2,-7,13,9,2,0,12,4,
0,0,-1,8,-3,-24,-8,6,3,-1};
staticdoubleb[10]={5,12,3,2,3,46,13,38,19,-21};
staticdoublex_jing[10]={1,-1,0,1,2,0,3,1,-1,2};//精确解
staticdoublex0[10]={0,0,0,0,0,0,0,0,0,0};
staticdoublex1[10];
staticintk,i,j;
//staticdoublea[8][8]={4,2,-4,0,2,4,0,0,
//2,2,-1,-2,1,3,2,0,
//-4,-1,14,1,-8,-3,5,6,
//矩阵B0,-2,1,6,-1,-4,-3,3,
//2,1,-8,-1,22,4,-10,-3,
//4,3,-3,-4,4,11,1,-4,
//0,2,5,-3,-10,1,14,2,
//0,0,6,3,-3,-4,2,19};
//staticdoubleb[8]={0,-6,6,23,11,-22,-15,45};
//staticdoublex_jing[8]={1,-1,0,2,1,-1,0,2};
//staticdoublex0[8]={0,0,0,0,0,0,0,0};
//staticdoublex1[8];
//staticdoublea[10][10]={4,-1,0,0,0,0,0,0,0,0,
//-1,4,-1,0,0,0,0,0,0,0,
//0,-1,4,-1,0,0,0,0,0,0,
//0,0,-1,4,-1,0,0,0,0,0,
//矩阵C0,0,0,-1,4,-1,0,0,0,0,
//0,0,0,0,-1,4,-1,0,0,0,
//0,0,0,0,0,-1,4,-1,0,0,
//0,0,0,0,0,0,-1,4,-1,0,
//0,0,0,0,0,0,0,-1,4,-1,
//0,0,0,0,0,0,0,0,-1,4};
//staticdoubleb[10]={7,5,-13,2,6,-12,14,-4,5,-5};
//staticdoublex_jing[10]={2,1,-3,0,1,-2,3,0,1,-1};
//staticdoublex0[10]={0,0,0,0,0,0,0,0,0,0};
doubleMax(inty)//求算该次迭代的误差
{
doublesum,max;
for(i=0;i
{
sum=0;
for(j=0;j
sum+=a[i][j]*x0[j];
x1[i]=x0[i]+(b[i]-sum)/a[i][i];
}
max=fabs(x_jing[0]-x1[0]);
for(i=1;i
{
if(fabs(x_jing[i]-x1[i])>max)
max=fabs(x_jing[i]-x1[i]);
}
cout<<"第"<returnmax;
}
voidmain()
{
doublee[3]={10e-3,10e-4,10e-5};
doublemax;
intt;
cout<<"请选择精确度:
0、10e-31、10e-42、103-5";
cin>>t;
for(k=0;k{
max=Max(k);
if(max{k=k;
break;}
else
{
for(i=0;i
x0[i]=x1[i];
}
}
if(k{
cout<<"迭代次数为"<cout<<"方程组的解为"<for(i=0;i
cout<<""<}
else
{
cout<<"迭代次数超过"<"<cout<<"方程组的解为"<for(i=0;i
cout<<""<}
}
//Gauss-Seidol.cpp
#include
#include
usingnamespacestd;
#defineN15//最大迭代次数
//#defineP10//矩阵的阶数
#defineP8
//staticdoublea[10][10]={4,2,-3,-1,2,1,0,0,0,0,
//8,6,-5,-3,6,5,0,1,0,0,
//4,2,-2,-1,3,2,-1,0,3,1,
//0,-2,1,5,-1,3,-1,1,9,4,
//-4,2,6,-1,6,7,-3,3,2,3,
//8,6,-8,5,7,17,2,6,-3,5,
//0,2,-1,3,-4,2,5,3,0,1,
//16,10,-11,-9,17,34,2,-1,2,2,
//4,6,2,-7,13,9,2,0,12,4,
//0,0,-1,8,-3,-24,-8,6,3,-1};
//staticdoubleb[10]={5,12,3,2,3,46,13,38,19,-21};
//staticdoublex_jing[10]={1,-1,0,1,2,0,3,1,-1,2};//精确解
//staticdoublex0[10]={0,0,0,0,0,0,0,0,0,0};
//staticdoublex1[10];
staticintk,i,j;
staticdoublea[8][8]={4,2,-4,0,2,4,0,0,
2,2,-1,-2,1,3,2,0,
-4,-1,14,1,-8,-3,5,6,
0,-2,1,6,-1,-4,-3,3,
2,1,-8,-1,22,4,-10,-3,
4,3,-3,-4,4,11,1,-4,
0,2,5,-3,-10,1,14,2,
0,0,6,3,-3,-4,2,19};
staticdoubleb[8]={0,-6,6,23,11,-22,-15,45};
staticdoublex_jing[8]={1,-1,0,2,1,-1,0,2};
staticdoublex0[8]={0,0,0,0,0,0,0,0};
staticdoublex1[8];
//staticdoublea[10][10]={4,-1,0,0,0,0,0,0,0,0,
//-1,4,-1,0,0,0,0,0,0,0,
//0,-1,4,-1,0,0,0,0,0,0,
//0,0,-1,4,-1,0,0,0,0,0,
//矩阵C0,0,0,-1,4,-1,0,0,0,0,
//0,0,0,0,-1,4,-1,0,0,0,
//0,0,0,0,0,-1,4,-1,0,0,
//0,0,0,0,0,0,-1,4,-1,0,
//0,0,0,0,0,0,0,-1,4,-1
//0,0,0,0,0,0,0,0,-1,4};
//staticdoubleb[10]={7,5,-13,2,6,-12,14,-4,5,-5};
//staticdoublex_jing[10]={2,1,-3,0,1,-2,3,0,1,-1};//精确解
//staticdoublex0[10]={0,0,0,0,0,0,0,0,0,0};
doubleMax(inty)//求算该次迭代的误差
{
doublesum1,sum2,max;
for(i=0;i
{
sum1=0;
sum2=0;
for(j=0;j<=i-1;j++)
sum1+=a[i][j]*x1[j];
for(j=i+1;j
sum2+=a[i][j]*x0[j];
x1[i]=(b[i]-sum1-sum2)/a[i][i];
}
max=fabs(x_jing[0]-x1[0]);
for(i=1;i
{
if(fabs(x_jing[i]-x1[i])>max)
max=fabs(x_jing[i]-x1[i]);
}
cout<<"第"<returnmax;
}
voidmain()
{
doublee[3]={10e-3,10e-4,10e-5};
doublemax;
intt;
cout<<"请选择精确度:
0、10e-31、10e-42、103-5";
cin>>t;
for(k=0;k{
max=Max(k);
if(max{k=k;
break;}
else
{
for(i=0;i
x0[i]=x1[i];
}
}
if(k{
cout<<"迭代次数为"<cout<<"方程组的解为"<for(i=0;i
cout<<""<}
else
{
cout<<"迭代次数超过"<"<cout<<"方程组的解为"<for(i=0;i
cout<<""<}
}
//SOR.cpp
#include
#include
usingnamespacestd;
#defineN15//最大迭代次数
#defineP10//矩阵的阶数
//#defineP8
//staticdoublea[10][10]={4,2,-3,-1,2,1,0,0,0,0,
//8,6,-5,-3,6,5,0,1,0,0,
//4,2,-2,-1,3,2,-1,0,3,1,
//矩阵A0,-2,1,5,-1,3,-1,1,9,4,
//-4,2,6,-1,6,7,-3,3,2,3,
//8,6,-8,5,7,17,2,6,-3,5,
//0,2,-1,3,-4,2,5,3,0,1,
//16,10,-11,-9,17,34,2,-1,2,2,
//4,6,2,-7,13,9,2,0,12,4,
//0,0,-1,8,-3,-24,-8,6,3,-1};
//staticdoubleb[10]={5,12,3,2,3,46,13,38,19,-21};
//staticdoublex_jing[10]={1,-1,0,1,2,0,3,1,-1,2};//精确解
//staticdoublex0[10]={0,0,0,0,0,0,0,0,0,0};
staticdoublex1[P];
staticdoublesumx[P];
staticintk,i,j;
//staticdoublea[8][8]={4,2,-4,0,2,4,0,0,
//2,2,-1,-2,1,3,2,0,
//-4,-1,14,1,-8,-3,5,6,
//矩阵B0,-2,1,6,-1,-4,-3,3,
//2,1,-8,-1,22,4,-10,-3,
//4,3,-3,-4,4,11,1,-4,
//0,2,5,-3,-10,1,14,2,
//0,0,6,3,-3,-4,2,19};
//staticdoubleb[8]={0,-6,6,23,11,-22,-15,45};
//staticdoublex_jing[8]={1,-1,0,2,1,-1,0,2};
//staticdoublex0[8]={0,0,0,0,0,0,0,0};
//staticdoublex1[8];
staticdoublea[10][10]={4,-1,0,0,0,0,0,0,0,0,
-1,4,-1,0,0,0,0,0,0,0,
0,-1,4,-1,0,0,0,0,0,0,
0,0,-1,4,-1,0,0,0,0,0,
0,0,0,-1,4,-1,0,0,0,0,
0,0,0,0,-1,4,-1,0,0,0,
0,0,0,0,0,-1,4,-1,0,0,
0,0,0,0,0,0,-1,4,-1,0,
0,0,0,0,0,0,0,-1,4,-1,
0,0,0,0,0,0,0,0,-1,4};
staticdoubleb[10]={7,5,-13,2,6,-12,14,-4,5,-5};
staticdoublex_jing[10]={2,1,-3,0,1,-2,3,0,1,-1};//精确解
staticdoublex0[10]={0,0,0,0,0,0,0,0,0,0};
doubleMax(doublew,doubley)
{
doublesum1,sum2,max;
for(i=0;i
{
sum1=0;
sum2=0;
for(j=0;j<=i-1;j++)
sum1+=a[i][j]*x1[j];
for(j=i;j
sum2+=a[i][j]*x0[j];
sumx[i]=w*(b[i]-sum1-sum2)/a[i][i];
x1[i]=x0[i]+sumx[i];
}
max=fabs(x_jing[0]-x1[0]);
for(i=1;i
{
if(fabs(x_jing[i]-x1[i])>max)
max=fabs(x_jing[i]-x1[i]);
}
cout<<"第"<returnmax;
}
voidmain()
{
doublee[3]={10e-3,10e-4,10e-5};
doublew[5]={0.8,0.9,1,1.1,1.2};
doublemax;
intt,l;
cout<<"请选择精确度:
0、10e-31、10e-42、103-5";
cin>>t;
cout<<"请选择松弛因子:
0、0.81、0.92、13、1.14、1.2";
cin>>l;
for(k=0;k{
max=Max(w[l],k);
if(max{k=k;
break;}
else
{
for(i=0;i
x0[i]=x1[i];
}
}
if(k{
cout<<"迭代次数为"<cout<<"方程组的解为"<for(i=0;i
cout<<""<}
else
{
cout<<"迭代次数超过"<"<cout<<"方程组的解为"<for(i=0;i
cout<<""<}
}
【运行结果】
方程A:
=
Jacobi迭代
Gauss-Seidol迭代
SOR迭代
方程B
Jacobi迭代
Gauss-Seidol迭代
SOR迭代
方程C
Jacobi迭代
Gauss-Seidol迭代(选取了不同的精度)
SOR迭代(选取了不同的松弛因子)
【结果分析】
1、通过实验结果看出(方程C的Gauss-Seidol迭代),取的精度不同,迭代的次数也不同。
精度越大,迭代次数越多。
2、通过实验结果看出(方程C的SOR迭代),取的松弛因子的大小不同,迭代的次数不同,其中ω=1的时候,为Gauss-Seidol迭代。
而松弛因子的取值影响着迭代次数,最佳松弛因子为使ρ(Lω)达到最小的ω。
本实验中方程C最佳的ω为1。