Блок-схема метода Гаусса-Зейделя.
gradf1=11+2*x1*exp(x1*x1+0.21*x2*x2); gradf2=-0.4+0.42*x2*exp(x1*x1+0.21*x2*x2);

p++;
k=2*p; grad[1]=
gradf1 (x1[k],x2[k],1); grad[2]=
gradf2 (x1[k],x2[k],2); N1=N1+2;
нет да
да нет
x1=a+(b-a)/(l*l); x2=a+(b-a)/l;
N=N+2;
E=0.0001 y1=11*(
x1[k]-x1*grad1)-0.4*
x2[k]+exp(pow((x1[k]-x1*grad1),2)+0.21*pow(x2[k],2)) y2=11*
x1[k]-0.4*(
x2[k]-x2*grad2)+exp(pow(x1[k],2)+0.21*pow((x2[k]-x2*grad2),2))
нет да
да нет
нет да
grad[1]=
gradf1 (x1[k+1],x2[k+1],1); grad[2]=
gradf2 (x1[k+1],x2[k+1],2); N1=N1+2;
shag=0.17;
m=0; N++; Y1=11*(
x1[k+1]-0*grad1)-0.4*
x2[k+1]+exp(pow((x1[k+1]-0*grad1),2)+0.21*pow(x2[k+1],2))
C=(m+1)*shag;
N++ Y2
=11* x1[k+1]-0.4*(
x2[k+1]-C*grad2)+exp(pow(x1[k+1],2)+0.21*pow((x2[k+1]-C*grad2),2))
m=m+1;
Y1=Y2 b=C



a=0 a=(m+1)*shag




x1=a+(b-a)/(l*l);
l=1.618; x2=a+(b-a)/l;
N=N+2; E=0.0001 y1=11*(
x1[k+1]-x1*grad1)-0.4*
x2[k+1]+exp(pow((x1[k+1]-x1*grad1),2)+0.21*pow(x2[k+1],2)) y2=11*
x1[k+1]-0.4*(
x2[k+1]-x2*grad2)+exp(pow(x1[k+1],2)+0.21*pow((x2[k+1]-x2*grad2),2))

нет
да



b=x2;
x2=x1; y2=y1; x1=a+b-x2;
y1=f(x1); a=x1;
x1=x2; y1=y2; x2=a+b-x1;
y2=f(x2);


N=N++;
да
нет
нет
да
alfa=(a+x2)/2 alfa=(x1+b)/2


x2[k+2]=x2[k+1]-alfa*grad[2] x1[k+2]=x1[k+1];
Z=sqrt(
pow((x1[k+2]-x1[k]),2) + pow((x2[k+2]-x2[k]),2) )
да
нет



minx1=x1[k+2]; minx2=x2[k+2]; miny=fx(x1[k+2],x2[k+2]);
Листинги программ.
Поиск по образцу
#include <iostream.h>
#include <stdio.h>
#include <math.h>
#include <conio.h>
long int t=0;
long double fx(long double x1,long double x2);
int main(){
cout<<"Metod poiska po obrazcu."<<endl;
long double **x = new long double *[2];
for(int p=0;p<5;p++)
x[p]=new long double[6];
x[1][0]=-1;
x[2][0]=0;
long double h=0.09,e=0.0001;
long double *y=new long double[6];
y[0]=fx(x[1][0],x[2][0]);
int k=0;
metka:
if (k!=1){
x[1][1]=x[1][0]-h;
x[2][1]=x[2][0]-h;
y[1]=fx(x[1][1],x[2][1]);
cout<<"x11="<<x[1][1]<<" x21="<<x[2][1]<<endl;
}
if (k!=2){
x[1][2]=x[1][0]-h;
x[2][2]=x[2][0]+h;
y[2]=fx(x[1][2],x[2][2]);
cout<<"x12="<<x[1][2]<<" x22="<<x[2][2]<<endl; }
if (k!=3){
x[1][3]=x[1][0]+h;
x[2][3]=x[2][0]+h;
y[3]=fx(x[1][3],x[2][3]);
cout<<"x13="<<x[1][3]<<" x23="<<x[2][3]<<endl; }
if (k!=4){
x[1][4]=x[1][0]+h;
x[2][4]=x[2][0]-h;
y[4]=fx(x[1][4],x[2][4]);
cout<<"x14="<<x[1][4]<<" x24="<<x[2][4]<<endl; }
k=0;
int l=1;
for(int i=1;i<5;i++) {
if(y[i]<y[l]) l=i;
}
if(y[l]<y[0]){ if(l>2) {x[1][l-2]=x[1][0];x[2][l-2]=x[2][0];y[l-2]=y[0];k=l-2;}
else {x[1][l+2]=x[1][0];x[2][l+2]=x[2][0];y[l+2]=y[0];k=l+2;}
x[1][0]=x[1][l];x[2][0]=x[2][l];y[0]=y[l];
goto metka;}
else{
h=h/2;
if(h>e){goto metka;}
else{long double minx1,minx2,minf;
minx1=x[1][0];
minx2=x[2][0];
minf=y[0];
cout<<"minx1="<<minx1<<" minx2="<<minx2<<" minf="<<minf<<endl;
cout<<"N="<<t<<endl;
getch();
return(0); }
}
}
long double fx(long double x1,long double x2){
t=t++;
long double f;
f=11*x1-0.4*x2+exp(x1*x1+0.21*x2*x2);
return(f);}
Симплекс метод
#include <iostream.h>
#include <stdio.h>
#include <math.h>
#include <conio.h>
long int t=0;
long double fx(long double x1,long double x2);
long double gradfx(long double x1,long double x2,short int r);
int i,j;
int main(){
cout<<"Metod simpleksa."<<endl;
long double **x = new long double *[2];
for(int p=1;p<3;p++)
x[p]=new long double[200];
x[1][0]=-1;
x[2][0]=0;
long double r=2.5,e=0.0001;
x[1][1]=x[1][0]+r;
x[2][1]=x[2][0];
x[1][2]=x[1][0];
x[2][2]=x[2][0]+r;
cout<<"x11="<<x[1][1]<<" x21="<<x[2][1]<<endl;
cout<<"x12="<<x[1][2]<<" x22="<<x[2][2]<<endl;
long double *y=new long double[4]; //y3=y
y[0]=fx(x[1][0],x[2][0]);
y[1]=fx(x[1][1],x[2][1]);
y[2]=fx(x[1][2],x[2][2]);
long double c1,c2,u1,u2;
int l1,l2;
metka:
l1=0,l2=0;
for(int i=0;i<3;i++) {
if(y[i]<y[l1]) l1=i;
}
for(int j=0;j<3;j++) {
if(y[j]>y[l2]) l2=j;
}
if(r>e){c1=0,c2=0;
for(int i=0;i<3;i++)
if(i!=l2) {c1+=x[1][i];c2+=x[2][i];}
c1/=2; c2/=2;
u1=2*c1-x[1][l2];
u2=2*c2-x[2][l2];
y[3]=fx(u1,u2);
//постоение нового симплекса
if(y[3]<y[l2]){x[1][l2]=u1;x[2][l2]=u2;y[l2]=y[3];
cout<<""<<x[1][l2]<<","<<x[2][l2]<<endl;}
else{ //cout<<"u1="<<u1<<" u2="<<u2<<endl;
for(int i=0;i<3;i++)
if(i!=l1){ x[1][i]=(x[1][i]+x[1][l1])/2;
x[2][i]=(x[2][i]+x[2][l1])/2;
y[i]=fx(x[1][i],x[2][i]);
cout<<""<<x[1][i]<<","<<x[2][i]<<endl;
}
r=r/2;
}
goto metka;
}
else{
long double minx1,minx2,minf;
minx1=x[1][l1];
minx2=x[2][l1];
minf=y[l1];
cout<<"minx1="<<minx1<<" minx2="<<minx2<<" minf="<<minf<<endl;
cout<<"N="<<t<<endl;
getch();
return(0);}
}
long double fx(long double x1,long double x2){
t++;
long double f;
f=11*x1-0.4*x2+exp(x1*x1+0.21*x2*x2);
return(f);}
Градиентный метод с дроблением шага
#include <iostream.h>
#include <stdio.h>
#include <math.h>
long int t=0,a=0;
long double fx(long double x1,long double x2);
long double gradfx(long double x1,long double x2,short int r);
int main(){
cout<<"gradientnii metod s drobleniem shaga."<<endl;
long double *x1=new long double [562];
long double *x2=new long double [562];
x1[0]=-1;
x2[0]=0;
long double alfa=0.39,e=0.0001,delta=0.1;
long double minx1,minx2,minf;
int k=0;
long double *grad = new long double [5];
long double D,y,z1;
grad[1]=gradfx(x1[0],x2[0],1);
grad[2]=gradfx(x1[0],x2[0],2);
D=pow(grad[1],2)+pow(grad[2],2);
metka2:
y=fx(x1[k],x2[k]);
metka:
z1=fx(x1[k]-alfa*grad[1],x2[k]-alfa*grad[2]);
if((z1-y)>-(alfa*delta*D)) {alfa=alfa/2; goto metka; }
else{
x1[k+1]=x1[k]-alfa*grad[1];
x2[k+1]=x2[k]-alfa*grad[2];
grad[1]=gradfx(x1[k+1],x2[k+1],1);
grad[2]=gradfx(x1[k+1],x2[k+1],2);
D=pow(grad[1],2)+pow(grad[2],2);}
if(sqrt(D)>e) { k++; goto metka2; }
else{
minx1=x1[k+1];
minx2=x2[k+1];
minf=fx(minx1,minx2);}
cout<<"minx1="<<minx1<<" minx2="<<minx2<<" minf="<<minf<<endl;
cout<<"N="<<t+a<<endl;
cout<<"k="<<k<<endl;
return(0);
}
long double fx(long double x1,long double x2){
a++; long double f;
f=11*x1-0.4*x2+exp(x1*x1+0.21*x2*x2);
return(f);}
long double gradfx(long double x1,long double x2,short int r){
::t++;
long double gradf;
if (r==1)
gradf=11+2*x1*exp(x1*x1+0.21*x2*x2);
if (r==2)
gradf=-0.4+0.42*x2*exp(x1*x1+0.21*x2*x2);
return(gradf);
}
Метод Гаусса-Зейделя
#include <iostream.h>
#include <stdio.h>
#include <math.h>
#include <conio.h>
int COUNT_F,COUNT_GRAD;
double function( double x1, double x2);
double proiz( double x1, double x2,short int r);
double odn_alg( double X1, double X2,short int s);
double __function(const double X1,const double X2, double alfa, double grad1, double grad2,short int v);
void ab(double &a,double &b,const double X1,const double X2,double grad1,double grad2,short int u);
int main(){
double x1[1000];
double x2[1000];
int p=-1,k;
x1[0]=-1;
x2[0]=0;
double grad[3]; double e=0.0001;double alfa;
cout<<"Metod Gayssa-Zeidela"<<endl;
do{
p++; k=2*p;
grad[1]=proiz(x1[k],x2[k],1);
alfa=odn_alg(x1[k],x2[k],1);
x1[k+1]=x1[k]-alfa*grad[1];
x2[k+1]=x2[k];
cout<<"x11="<<x1[k+1]<<" x21="<<x2[k+1]<<endl;
grad[2]=proiz(x1[k+1],x2[k+1],2);
alfa=odn_alg(x1[k+1],x2[k+1],2);
x2[k+2]=x2[k+1]-alfa*grad[2];
x1[k+2]=x1[k+1];
cout<<"x12="<<x1[k+2]<<" x22="<<x2[k+2]<<endl;
}while( sqrt( pow((x1[k+2]-x1[k]),2) + pow((x2[k+2]-x2[k]),2) ) > e);
double minx1,minx2,miny;
minx1=x1[k+2];
minx2=x2[k+2];
miny=function(x1[k+2],x2[k+2]);
printf("~x=(%f,%f),~y=%f,iterations=%i,func=%i,grad=%i\n",x1[k+2],x2[k+2],miny,k,COUNT_F-1,COUNT_GRAD);
getch();
return(0);
}
double function( double x1, double x2){
double f;
f=11*x1-0.4*x2+exp(x1*x1+0.21*x2*x2);
COUNT_F++;
return(f);}
double proiz( double x1, double x2,short int r){
COUNT_GRAD++;
double gradf;
if (r==1)
gradf=11+2*x1*exp(x1*x1+0.21*x2*x2);
if (r==2)
gradf=-0.4+0.42*x2*exp(x1*x1+0.21*x2*x2);
return(gradf);
}
double __function(const double X1,const double X2, double alfa, double grad1, double grad2,short int v)
{
COUNT_F++;
double rezt;
if(v==1)
rezt=11*(X1-alfa*grad1)-0.4*X2+exp(pow((X1-alfa*grad1),2)+0.21*pow(X2,2));
if(v==2)
rezt=11*X1-0.4*(X2-alfa*grad2)+exp(pow(X1,2)+0.21*pow((X2-alfa*grad2),2));
return(rezt);
}
inline double odn_alg( double X1, double X2,short int s){ //МЗС
double const l=(1+sqrt(5))/2;
double a,b,x1,x2,y1,y2,minx,z,E=0.0001;
double *grad=new double[3];
if(s==1)
{
ab(a,b,X1,X2,grad[1],grad[2],1);
x1=a+(b-a)/(l*l);
x2=a+(b-a)/l;
y1=__function(X1,X2,x1,grad[1],grad[2],1);
y2=__function(X1,X2,x2,grad[1],grad[2],1);
metka: {
if (y1<=y2) {
b=x2; x2=x1; y2=y1; x1=a+b-x2;
y1=__function(X1,X2,x1,grad[1],grad[2],1);}
else {
a=x1; x1=x2; y1=y2; x2=a+b-x1;
y2=__function(X1,X2,x2,grad[1],grad[2],1);}
}
z=(b-a)/(2*l);
if(z>E)
{ goto metka;}
else if(y1<y2)
{minx=(a+x2)/2;}
else
{minx=(x1+b)/2;}
}
else
{
ab(a,b,X1,X2,grad[1],grad[2],2);
x1=a+(b-a)/(l*l);
x2=a+(b-a)/l;
y1=__function(X1,X2,x1,grad[1],grad[2],2);
y2=__function(X1,X2,x2,grad[1],grad[2],2);
met: {
if (y1<=y2) {
b=x2; x2=x1; y2=y1; x1=a+b-x2;
y1=__function(X1,X2,x1,grad[1],grad[2],2);}
else {
a=x1; x1=x2; y1=y2; x2=a+b-x1;
y2=__function(X1,X2,x2,grad[1],grad[2],2);}
}
z=(b-a)/(2*l);
if(z>E)
{ goto met;}
else if(y1<y2)
{minx=(a+x2)/2;}
else
{minx=(x1+b)/2;}
}
return(minx);}
void ab(double &a,double &b,const double X1,const double X2,double grad1,double grad2,short int u)
{
double m=0,C,Y1,Y2;
double *grad=new double[3];
grad[1]=proiz(X1,X2,1);
grad[2]=proiz(X1,X2,2);
if(u==1)
{
long double shag=0.019;
Y1=__function(X1,X2,0,grad[1],grad[2],1);
metka2:
C=(m+1)*shag;
Y2=__function(X1,X2,C,grad[1],grad[2],1);
if(Y2<Y1) { m=m+1; Y1=Y2; goto metka2;}
else { b=C; }
if(m==0) {a=0;}
else {a=(m+1)*shag; }
}
else //u=2
{long double shag=0.17;
Y1=__function(X1,X2,0,grad[1],grad[2],2);
met2:
C=(m+1)*shag;
Y2=__function(X1,X2,C,grad[1],grad[2],2);
if(Y2<Y1) { m=m+1; Y1=Y2; goto met2;}
else { b=C; }
if(m==0) {a=0;}
else {a=(m+1)*shag; }
}
return;
}
