外推法c语言,共轭梯度法,黄金分割,外推法C语言代码

共轭梯度法求函数极小值的方法,利用到了黄金分割和外推法求方向上的极小值。

#include

#include

#define lamda 0.618

//************************

float a,b,c,d,e,g;//目标函数的系数

float x1,x2,arf;//目标函数的变量

float a0[2],b0[2],c0[2];//一维搜索区间的变量定义

float xi1,xi2,xi3,xi4;

float min_gold_x[2];

float directon[2];//搜索方向

float powell_minx[2],xg_min[2];

float _g[2];

//***********************************

void get_num()

{

printf("输入目标函数系数\n");

scanf("%f %f %f %f %f %f",&a,&b,&c,&d,&g,&e);

printf("a=%f b=%f c=%f d=%f e=%f g=%f\n",a,b,c,d,e,g);

printf("\n目标函数为:\n");

printf("y=%f*x1*x1+%f*x2*x2+%f*x1+%f*x2+%f*x1*x2+%f\n",a,b,c,d,g,e);

}

//功能函数***************************

float fun(float x1,float x2)

{

float y;

y=a*x1*x1+b*x2*x2+c*x1+d*x2+g*x1*x2+e;

return y;

}

//*********计算步长***

float change(float h0,float d[2])

{

float m,n;

n=(d[0]*d[0]+d[1]*d[1])/(h0*h0);

m=sqrt(n);

return m;

}

//***区间搜索********************

void search(float x01,float x02,float h0,float d[2])

{

float y0,y1,y2,n,di[2],x1[2],x2[2],x0[2];

int j,k=0;

for(j=0;j<2;j++)//读取搜索方向

{

di[j]=d[j];

}

x0[0]=x01,x0[1]=x02;

n=change(h0,di);

di[0]=di[0]/n;

di[1]=di[1]/n;

x1[0]=x0[0]+di[0];

x1[1]=x0[1]+di[1];

y0=fun(x0[0],x0[1]);

y1=fun(x1[0],x1[1]);

if(y1<=y0)

{

for(j=0;j<2;j++)

{

di[j]=2*di[j];

x2[j]=x1[j]+di[j];

}

}

if(y1>y0)

{

for(j=0;j<2;j++)

{

di[j]=(-2)*di[j];

x2[j]=x1[j]+di[j];

}

}

while(1)

{

y2=fun(x2[0],x2[1]);

if(y2<=y1)

{

y0=y1;y1=y2;

for(j=0;j<2;j++)

{

x0[j]=x1[j];

x1[j]=x2[j];

}

for(j=0;j<2;j++)

{

di[j]=2*di[j];

x2[j]=x1[j]+di[j];

}

}

if(y2>y1)

{

for(j=0;j<2;j++)

{

a0[j]=x0[j];

b0[j]=x1[j];

c0[j]=x2[j];

}

break;

}

}

}

//*********************黄金分割********************

void gold_d(float a[2],float b[2],float dlt)

{

float alf1[2],alf2[2],y1,y2;

float at[2],bt[2],temp1[2],temp2[2];

float m,n,i,k;

int j;

/*dlt=dlt*dlt;*/

for(j=0;j<2;j++)

{

at[j]=a[j];

bt[j]=b[j];

}

for(j=0;j<2;j++)

{

alf1[j]=bt[j]-lamda*(bt[j]-at[j]);

alf2[j]=at[j]+lamda*(bt[j]-at[j]);

}

y1=fun(alf1[0],alf1[1]);

y2=fun(alf2[0],alf2[1]);

while(1)

{

if(y1>=y2)

{

for(j=0;j<2;j++)

{

at[j]=alf1[j];

alf1[j]=alf2[j];

}

y1=y2;

for(j=0;j<2;j++)

{

alf2[j]=at[j]+lamda*(bt[j]-at[j]);

}

y2=fun(alf2[0],alf2[1]);

}

else

{

for(j=0;j<2;j++)

{

bt[j]=alf2[j];

alf2[j]=alf1[j];

}

y2=y1;

for(j=0;j<2;j++)

{

alf1[j]=bt[j]-lamda*(bt[j]-at[j]);

}

y1=fun(alf1[0],alf1[1]);

}

for(j=0;j<2;j++)

{

temp1[j]=bt[j]-at[j];

}

n=(y2-y1)/y2;n=fabs(n);

m=temp1[0]*temp1[0]+temp1[1]*temp1[1];

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值