Modified Strongly Implicit Procedure (MSIP) 代码

此方法解九对角矩阵

根据

A modified strongly implicit procedure for the numerical solution of field problems
GE Schneider, M Zedan - Numerical Heat Transfer, 1981 - Taylor & Francis
的思路,原文看不到

参考 计算传热学近代进展 (书上公式有误)

// MSIP.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
double abs(double a){
	if(a>=0){
		return a;
	}else{
		return -a;
	}
}

int MSIPsolver(double *Aa, double *Ab, double *Ac, double *Ad, double *Ae, 
			  double *Af, double *Ag, double *Ah, double *As, 
			  double *x,double* r, int m,int n)
{
	double ALF=0.6;
	double P1=0;
	double P2=0;
	double *La,*Lb,*Lc,*Ld,*Le,*Uf,*Ug,*Uh,*Us;
	double *RES;
	double RESN=0;
	int MAXITER=1000;
	int ITER;
	La=new double [n+1];
	Lb=new double [n+1];
	Lc=new double [n+1];
	Ld=new double [n+1];
	Le=new double [n+1];
	Uf=new double [n+1];
	Ug=new double [n+1];
	Uh=new double [n+1];
	Us=new double [n+1];
	RES=new double [n+1];
	for(int i=0;i<=n;i++){
		La[i]=0;
		Lb[i]=0;
		Lc[i]=0;
		Ld[i]=0;
		Le[i]=0;
		Uf[i]=0;
		Ug[i]=0;
		Uh[i]=0;
		Us[i]=0;
		RES[i]=0;
	}
	for(int i=0;i<=n;i++)
	{
		//La-----------------
		if(i>=m+1){
			La[i]= Aa[i];
		}else{
			La[i]=0;
		}
		//Lb-----------------
		if(i>=m){
			Lb[i]= Ab[i] - La[i]*Uf[i-m-1] - ALF*Lc[i]*Uf[i-m+1];
		}else{
			Lb[i]=0;
		}
		//Lc-----------------
		if(i>=m-1){
			Lc[i]= Ac[i] - Lb[i]*Uf[i-m];
		}else{
			Lc[i]= 0;
		}
		//Ld-----------------
		if(i>=1){
			Ld[i]= (Ad[i] - La[i]*Uh[i-m-1] - Lb[i]*Ug[i-m] - 2*ALF*La[i]*Ug[i-m-1])/(2*ALF*Ug[i-1] + 1);
		}else{
			Ld[i]=0;
		}
		//Le-----------------
		Le[i]= Ae[i] - Lb[i]*Uh[i-m] - Lc[i]*Ug[i-m+1] - Ld[i]*Uf[i-1] - La[i]*Us[i-m-1] + ALF*La[i]*Ug[i-m-1] - 2*ALF*Lc[i]*Uf[i-m+1] + 2*ALF*Ld[i]*Ug[i-1] + ALF*Lc[i]*Us[i-m+1];
		//Uf-----------------
		if(i<=n-1){	
			Uf[i]= (Af[i] - Lc[i]*Uh[i-m+1] - Lb[i]*Us[i-m] + 2*ALF*Lc[i]*Uf[i-m+1] - 2*ALF*Lc[i]*Us[i-m+1])/Le[i];
		}else{
			Uf[i]=0;
		}
		//Ug-----------------
		if(i<=n-m+1){
			Ug[i]= (Ag[i] - Ld[i]*Uh[i-1])/Le[i];
		}else{
			Ug[i]=0;
		}
		//Uh-----------------
		if(i<=n-m){
			Uh[i]= (Ah[i] - Ld[i]*Us[i-1] - ALF*Ld[i]*Ug[i-1])/Le[i];
		}else{
			Uh[i]=0;
		}
		//Us-----------------
		if(i<=n-m-1){
			Us[i]= As[i]/Le[i];
		}else{
			Us[i]= 0;
		}
	}
	ITER=0;
	do{
		RESN=0;
		for(int i=0;i<=n;i++)
		{
			RES[i]=r[i]-(Aa[i]*(i-m-1>=0?x[i-m-1]:0)
						+Ab[i]*(i-m>=0?x[i-m]:0)
						+Ac[i]*(i-m+1>=0?x[i-m+1]:0)
						+Ad[i]*(i-1>=0?x[i-1]:0)
						+Ae[i]*x[i]
						+Af[i]*(i+1<=n?x[i+1]:0)
						+Ag[i]*(i+m-1<=n?x[i+m-1]:0)
						+Ah[i]*(i+m<=n?x[i+m]:0)
						+As[i]*(i+m+1<=n?x[i+m+1]:0));
			RESN+=abs(RES[i]);
		}

		for(int i=0;i<=n;i++)
		{
			RES[i]=(RES[i]-La[i]*(i-m-1>=0?RES[i-m-1]:0)
					-Lb[i]*(i-m>=0?RES[i-m]:0)
					-Lc[i]*(i-m+1>=0?RES[i-m+1]:0)
					-Ld[i]*(i-1>=0?RES[i-1]:0))/Le[i];
		}
		
		for(int i=n;i>=0;i--)
		{
			x[i]=x[i]+(RES[i]-Uf[i]*(i+1<=n?RES[i+1]:0)
							-Ug[i]*(i+m-1<=n?RES[i+m-1]:0)
							-Uh[i]*(i+m<=n?RES[i+m]:0)
							-Us[i]*(i+m+1<=n?RES[i+m+1]:0));
		}
		ITER++;
	}while(abs(RESN)>1E-6&&ITER<MAXITER);
	
	delete [] La;
	delete [] Lb;
	delete [] Lc;
	delete [] Ld;
	delete [] Le;
	delete [] Uf;
	delete [] Ug;
	delete [] Uh;
	delete [] Us;
	delete [] RES;
	return ITER>MAXITER?-1:1;
}


int _tmain(int argc, _TCHAR* argv[])
{
	const int n=29;
	int m=6;
	//Define a b c d e f g h s
	double Aa[n+1],Ab[n+1],Ac[n+1],Ad[n+1],Ae[n+1],Af[n+1],Ag[n+1],Ah[n+1],As[n+1],x[n+1],xr[n+1],r[n+1];
	for(int i=0;i<=n;i++){
		i>=m+1?Aa[i]=1:Aa[i]=0;
		i>=m?Ab[i]=2:Ab[i]=0;
		i>=m-1?Ac[i]=1:Ac[i]=0;
		i>=1?Ad[i]=3:Ad[i]=0;
		Ae[i]=18;
		i<=n-1?Af[i]=3:Af[i]=0;
		i<=n-m+1?Ag[i]=1:Ag[i]=0;
		i<=n-m?Ah[i]=2:Ah[i]=0;
		i<=n-m-1?As[i]=1:As[i]=0;
		r[i]=i+2;
		x[i]=1;
	}
	for(int i=0;i<=n;i++){
		printf("Aa[%d]=%.2f  ",i,Aa[i]);
		printf("Ab[%d]=%.2f  ",i,Ab[i]);
		printf("Ac[%d]=%.2f  ",i,Ac[i]);
		printf("Ad[%d]=%.2f  ",i,Ad[i]);
		printf("Ae[%d]=%.2f  ",i,Ae[i]);
		printf("\n");
	}

	for(int i=0;i<=n;i++){
		printf("Af[%d]=%.2f  ",i,Af[i]);
		printf("Ag[%d]=%.2f  ",i,Ag[i]);
		printf("Ah[%d]=%.2f  ",i,Ah[i]);
		printf("As[%d]=%.2f  ",i,As[i]);
		printf("r[%d]=%.2f   ",i,r[i]);
		printf("\n");
	}
	xr[0]=0.0419;
	xr[1]=0.0777;
	xr[2]=0.1145;
	xr[3]=0.151;
	xr[4]=0.1878;
	xr[5]=0.2227;
	xr[6]=0.2534;
	xr[7]=0.2831;
	xr[8]=0.3135;
	xr[9]=0.3436;
	xr[10]=0.3741;
	xr[11]=0.4062;
	xr[12]=0.4398;
	xr[13]=0.4732;
	xr[14]=0.505;
	xr[15]=0.5368;
	xr[16]=0.569;
	xr[17]=0.5925;
	xr[18]=0.6064;
	xr[19]=0.6266;
	xr[20]=0.6551;
	xr[21]=0.69;
	xr[22]=0.705;
	xr[23]=0.7724;
	xr[24]=0.9334;
	xr[25]=1.0289;
	xr[26]=1.0547;
	xr[27]=1.1003;
	xr[28]=1.0966;
	xr[29]=1.3626;

	//for(int i=0;i<=n;i++){
	//	printf("xr[%d]=%.6f  ",i,xr[i]);
	//	printf("\n");
	//}
	printf("-----------------------------\n");
	MSIPsolver(Aa,Ab,Ac,Ad,Ae,Af,Ag,Ah,As,x,r,m,n);
	for(int i=0;i<=n;i++){
		printf("x[%d]=%.6f    ",i,x[i]);
		printf("xr[%d]=%.6f   ",i,xr[i]);
		printf("\n");
	}
	return 0;
}


你可能感兴趣的:(C++,解矩阵)