數據的輸入格式如下:
4,0.3,200.0,1 //分別爲:結點數、泊松比、楊氏模量和問題類型
0.0,1.0//依次爲四個結點的座標
1.0,1.0
1.0,0.0
0.0,0.0
1,2//單元編號
2,3
3,4
4,1
12,0.0,0.0//邊界條件
12,0.0,1.0
12,-1.0,0.0
12,0.0,-1.0
具體實現代碼如下,不敢保證絕對正確,目前只能算是Beta版本,最後輸出A和B矩陣爲AX=B方程的兩個矩陣,求解X可用Matlab用inv(A)*B得到。
#include <iostream>
#include <math.h>
#include <fstream>
using namespace std;
const double pi=3.14159265;
class DanYuan
{
public:
int StartID,EndID;
};
class Condition
{
public:
int Type;
double GivenTan,GivenNormal;
};
int Number;
double *X,*Y;
DanYuan *Element;
Condition *BianJie;
int PlaneType;
double v,E,G;
double **A,*B;
void ReadData()
{
char c;
int i;
ifstream read;
read.open("Data.txt",ios::in);
read>>Number>>c>>v>>c>>E>>c>>PlaneType;
if (PlaneType==1)
{
v=v/(1+v);
}
G=E/(2+2*v);
X=new double[Number+2];
Y=new double[Number+2];
Element=new DanYuan[Number+1];
BianJie=new Condition[Number+1];
A=new double *[2*Number+1];
for (i=1;i<=2*Number;i++)
{
A[i]=new double[2*Number+1];
}
B=new double[2*Number+1];
for (i=1;i<=Number;i++)
{
read>>X[i]>>c>>Y[i];
}
X[Number+1]=X[1];
Y[Number+1]=Y[1];
for (i=1;i<=Number;i++)
{
read>>Element[i].StartID>>c>>Element[i].EndID;
}
for (i=1;i<=Number;i++)
{
read>>BianJie[i].Type>>c>>BianJie[i].GivenTan>>c
>>BianJie[i].GivenNormal;
}
}
void ComputeGH(int i,int j,double Uknown[][3],double Known[][3])
{
double ri,r,r1,r2,dist,n1,n2;
double h11,h12,h21,h22,g11,g12,g21,g22;
double xc[5],yc[5],ax,ay,bx,by;
double guass[5],w[5];
h11=h12=h21=h22=g11=g12=g21=g22=0.0;
ax=X[Element[j].EndID]-X[Element[j].StartID];
ay=Y[Element[j].EndID]-Y[Element[j].StartID];
bx=X[Element[j].StartID]+X[Element[j].EndID];
by=Y[Element[j].StartID]+Y[Element[j].EndID];
w[1]=0.34785485;
w[2]=w[1];
w[3]=0.65214515;
w[4]=w[3];
guass[1]=0.86113631;
guass[2]=-guass[1];
guass[3]=0.33998104;
guass[4]=-guass[3];
if (i==j)
{
r=sqrt(ax*ax+ay*ay);
r1=abs(ax/r);
r2=abs(ay/r);
double temp=r/(8*pi*G*(1-v));
h11=0.5;h12=0.0;
h12=0.0;h22=0.5;
g11=temp*((3-4*v)*(1-log(r/2))+r1*r1);
g12=temp*r2*r1;
g21=g12;
g22=temp*((3-4*v)*(1-log(r/2))+r2*r2);
switch(BianJie[j].Type)
{
case 12:
Uknown[1][1]=g11;
Uknown[1][2]=g12;
Uknown[2][1]=g21;
Uknown[2][2]=g22;
Known[1][1]=h11;
Known[1][2]=h12;
Known[2][1]=h21;
Known[2][2]=h22;
break;
}
}
else
{
double temp=1.0/(8.0*pi*G*(1-v));
double a,b,c;
a=ay;
b=-ax;
c=Y[Element[j].StartID]*ax-X[Element[j].StartID]*ay;
r=sqrt(ax*ax+ay*ay);
dist=abs(a*X[i]+b*Y[i]+c)/(sqrt(a*a+b*b));
n1=abs(ax/r);
n2=abs(ay/r);
for (int k=1;k<=4;k++)
{
xc[k]=-ax*guass[k]+bx;
yc[k]=-ay*guass[k]+by;
ri=sqrt(pow(xc[k]-X[i],2)+pow(yc[k]-Y[i],2));
r1=abs((xc[k]-X[i])/ri);
r2=abs((yc[k]-Y[i])/ri);
h11-=temp*2*dist*((1-2*v)+2*r1*r1)*(r/2)*w[k]/ri;
h12-=temp*2*(2*dist*r1*r2-(1-2*v)*(r1*n2-r2*n1))*(r/2)*w[k]/ri;
h21-=temp*2*(2*dist*r1*r2-(1-2*v)*(r2*n1-r1*n2))*(r/2)*w[k]/ri;
h22-=temp*2*dist*((1-2*v)+2*r2*r2)*(r/2)*w[k]/ri;
g11+=temp*((3-4*v)*log(1/ri)+r1*r1)*(r/2)*w[k];
g12+=temp*r1*r2*(r/2)*w[k];
g21+=temp*r1*r2*(r/2)*w[k];
g22+=temp*((3-4*v)*log(1/ri)+r2*r2)*(r/2)*w[k];
}
switch(BianJie[j].Type)
{
case 12:
Uknown[1][1]=g11;
Uknown[1][2]=g12;
Uknown[2][1]=g21;
Uknown[2][2]=g22;
Known[1][1]=h11;
Known[1][2]=h12;
Known[2][1]=h21;
Known[2][2]=h22;
break;
}
}
}
void AssignA(double a[][3],int r,int c)
{
int i,j;
for (i=1;i<=2;i++)
{
for (j=1;j<=2;j++)
{
A[r+i-1][c+j-1]=a[i][j];
}
}
}
void CreateAXF()
{
int i,j;
double Uknown[3][3],Known[3][3];
for (i=1;i<=Number;i++)
{
B[2*i-1]=0.0;
B[2*i]=0.0;
for (j=1;j<=Number;j++)
{
ComputeGH(i,j,Uknown,Known);
AssignA(Uknown,2*i-1,2*j-1);
B[2*i-1]+=Known[1][1]*BianJie[j].GivenTan+
Known[1][2]*BianJie[j].GivenNormal;
B[2*i]+=Known[2][1]*BianJie[j].GivenTan+
Known[2][2]*BianJie[j].GivenNormal;
}
}
}
int main()
{
ReadData();
CreateAXF();
int i,j;
ofstream outa,outb;
outa.open("A.txt",ios::out);
outb.open("B.txt",ios::out);
for (i=1;i<=2*Number;i++)
{
for (j=1;j<=2*Number;j++)
{
outa<<A[i][j]<<" ";
}
outa<<endl;
}
for (j=1;j<=2*Number;j++)
{
outb<<B[j]<<endl;
}
return 0;
}