Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Скачиваний:
17
Добавлен:
02.05.2014
Размер:
117.76 Кб
Скачать

Министерство Образования Российской Федерации

Уфимский Государственный Авиационный Технический Университет

Кафедра ТК

Отчет по лабораторной работе №1

по предмету «Методы оптимизации»

на тему: Безусловная одномерная оптимизация

Выполнил: студент гр.Т28-320

Проверил: Хасанов А.Ю.

-Уфа, 2004 -

Лабораторная работа №1

Тема: Безусловная одномерная оптимизация

Методы: алгоритм блочного равномерного поиска;

алгоритм пассивного поиска минимума;

метод чисел Фибоначчи;

Задание: найти точку минимума функции f(x) = на отрезке [-1,0] при заданном числе экспериментов N=18.

Описание алгоритма в псевдокоде:

алгоритм F(x)

начало

скаляр ans=0; - вещественное

ans=x*x+exp(x);

возврат ans;

конец

алгоритм T(a, b, c, ya, yb, yc)

начало

скаляр x - вещественное

x=(b-c)*(b-c)*(ya-yc)-(c-a)*(c-a)*(yb-yc);

x=x/((b-c)*(ya-yc)+(c-a)*(yb-yc));

x=x/2;x+=c;

возврат (x);

конец

алгоритм **XY(a,b,ya,yb,n)

начало

массив XY[2][n+2] - вещественный

XY[0][0]=a;XY[1][0]=ya;

XY[0][n+1]=b;XY[1][n+1]=yb;

для i=1,i<=n, i++ повторить

начало

XY[0][i]=a+i*(b-a)/(n+1);

XY[1][i]=F(XY[0][i]);

конец

возврат XY;

конец

алгоритм **CXY(a, b, s, ya, yb, ys, n)

начало

вещественное **Tmp;

массив x[2][n+1] вещественный

xy[0][0]=a;xy[1][0]=ya;

xy[0][n+1]=b;xy[1][n+1]=yb;

если fmod(n,2)!=0 то

начало

Tmp=XY(a,s,ya,ys,(n-1)/2);

Для int i=1;i<=(n+1)/2;i++ повторить

начало

xy[0][i]=Tmp[0][i];

xy[1][i]=Tmp[1][i];

конец

Tmp=XY(s,b,ys,yb,(n-1)/2);

для int i=(n+1)/2;i<=n;i++)

начало

xy[0][i]=Tmp[0][i-(n+1)/2];

xy[1][i]=Tmp[1][i-(n+1)/2];

конец

конец

иначе

xy=XY(a,b,ya,yb,n);

все-если

возврат xy;

конец

алгоритм блочный поиск

начало

скаляры a=-1;ya=F(a);b=0;yb=F(b);s,ys;**xy; - вещественные

N=StrToInt(edtN->Text)-2;int n=StrToInt(edtD->Text);int ts=N/n; - Целые

xy=XY(a,b,ya,yb,n);

для i=2;i<=ts;i++ повторить

начало

c=xy[1][1];

t=1;

для k=2;k<=n;k++ повторить

если(xy[1][k]<c)началоc=xy[1][k];t=k;конец

a=xy[0][t-1];ya=xy[1][t-1];

b=xy[0][t+1];yb=xy[1][t+1];

s=xy[0][t];ys=xy[1][t];

xy=CXY(a,b,s,ya,yb,ys,n);

конец

вывод (b-a)/2,(a+b)/2

конец

алгоритм золотого сечения

начало

скаляры Lmb=1.618033989; a=-1; b=0; - Вещественные

N=StrToInt(edtN->Text); - Целое

x1=b-(b-a)/Lmb;x2=a+(b-a)/Lmb; y1=F(x1); y2=F(x2);- вещественное

для int i=1;i<=N;i++ повторить

начало

если (y1>y2) то

начало

a=x1;

x1=x2;y1=y2;

x2=a+(b-a)/Lmb;y2=F(x2);

конец

иначе

начало

b=x2;

x2=x1;y2=y1;

x1=b-(b-a)/Lmb;y1=F(x1);

конец

все-если

конец

вывод (fabs(b-a)/2),(b+a)/2;

конец

алгоритм метод парабол

начало

скаляры a=-1; b=0;

c=a+(b-a)/2; ya=F(a); yb=F(b);

yc=F(c); x=T(a,b,c,ya,yb,yc);

yx=F(x); - Вещественное

N=StrToInt(edtN->Text); - Целое

для int i=1;i<=N-4;i++ повторить

начало

fl=0;

если (x>c)то fl=1; все-если

если (x<c)то fl=2; все-если

если (x==c)то fl=3; все-если

выбрать (fl)

начало

case 1:

начало

если(yx>yc)начало b=x;yb=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);конец

иначе если(yx<yc)начало a=c;ya=yc;c=x;yc=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);конец

иначе если(yx==yc)начало a=c;ya=yc;b=x;yb=yx;c=(a+b)/2;yc=F(c);x=T(a,b,c,ya,yb,yc);

yx=F(x);i++;конец конец break;

case 2:

начало

если(yx>yc)начало a=x;ya=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);конец

иначе если(yx<yc)начало b=c;yb=yc;c=x;yc=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);конец

иначе если(yx==yc)началоa=x;ya=yx;b=c;yb=yc;c=(a+b)/2;yc=F(c);x=T(a,b,c,ya,yb,yc);

yx=F(x);i++;конец конец break;

case 3:началоx=(a+c)/2;yx=F(x);конец break;

конец

конец

вывод (fabs(b-a)/2),((b+a)/2);

конец

конец

Листинг программы:

Main.cpp

#include <vcl.h>

#pragma hdrstop

#include <math.h>

#include "Main.h"

#pragma package(smart_init)

#pragma resource "*.dfm"

long double F(long double x)

{

long double ans=0;

ans=x*x+exp(x);

return ans;

}

long double T(long double a,

long double b,

long double c,

long double ya,

long double yb,

long double yc)

{

long double x;

x=(b-c)*(b-c)*(ya-yc)-(c-a)*(c-a)*(yb-yc);

x=x/((b-c)*(ya-yc)+(c-a)*(yb-yc));

x=x/2;x+=c;

return (x);

}

long double **XY(long double a,long double b,long double ya,long double yb,int n)

{

long double **XY;

XY = new long double *[2];

XY[0] = new long double [n+2];

XY[1] = new long double [n+2];

XY[0][0]=a;XY[1][0]=ya;

XY[0][n+1]=b;XY[1][n+1]=yb;

for (int i=1;i<=n;i++)

{

XY[0][i]=a+i*(b-a)/(n+1);

XY[1][i]=F(XY[0][i]);

}

return XY;

}

long double **CXY(long double a, long double b, long double s,

long double ya,long double yb,long double ys,

int n)

{

long double **xy;

long double **Tmp;

xy = new long double *[2];

xy[0] = new long double [n+2];

xy[1] = new long double [n+2];

xy[0][0]=a;xy[1][0]=ya;

xy[0][n+1]=b;xy[1][n+1]=yb;

if(fmod(n,2)!=0)

{

Tmp=XY(a,s,ya,ys,(n-1)/2);

для int i=1;i<=(n+1)/2;i++)

{

xy[0][i]=Tmp[0][i];

xy[1][i]=Tmp[1][i];

}

Tmp=XY(s,b,ys,yb,(n-1)/2);

для int i=(n+1)/2;i<=n;i++)

{

xy[0][i]=Tmp[0][i-(n+1)/2];

xy[1][i]=Tmp[1][i-(n+1)/2];

}

}

else

xy=XY(a,b,ya,yb,n);

return xy;

}

TfrmMain *frmMain;

__fastcall TfrmMain::TfrmMain(TComponent* Owner)

: TForm(Owner)

{

для long double i=-1;i<=0.00;i+=0.05)

Series1->AddXY(i,F(i),"",clRed);

}

void __fastcall TfrmMain::btnCloseClick(TObject *Sender)

{

Close();

}

void __fastcall TfrmMain::btnSearchClick(TObject *Sender)

{

if (rbtn1->Checked)

{

long double a=-1;long double ya=F(a);

long double b=0;long double yb=F(b);

long double s,ys;

int N=StrToInt(edtN->Text)-2;

int n=StrToInt(edtD->Text);

int ts=N/n;

long double **xy;

xy=XY(a,b,ya,yb,n);

для int i=2;i<=ts;i++)

{

long double c=xy[1][1];

int t=1;

для int k=2;k<=n;k++)

if(xy[1][k]<c){c=xy[1][k];t=k;}

a=xy[0][t-1];ya=xy[1][t-1];

b=xy[0][t+1];yb=xy[1][t+1];

s=xy[0][t];ys=xy[1][t];

xy=CXY(a,b,s,ya,yb,ys,n);

}

edtE->Text=FloatToStr((b-a)/2);

edtX->Text=FloatToStr((a+b)/2);

}

if (rbtn2->Checked)

{

long double Lmb=1.618033989;

long double a=-1;

long double b=0;

int N=StrToInt(edtN->Text);

long double x1=b-(b-a)/Lmb;

long double x2=a+(b-a)/Lmb;

long double y1=F(x1);

long double y2=F(x2);

для int i=1;i<=N;i++)

{

if(y1>y2)

{

a=x1;

x1=x2;y1=y2;

x2=a+(b-a)/Lmb;y2=F(x2);

}

else

{

b=x2;

x2=x1;y2=y1;

x1=b-(b-a)/Lmb;y1=F(x1);

}

}

edtE->Text=FloatToStr(fabs(b-a)/2);

edtX->Text=FloatToStr((b+a)/2);

}

if(rbtn3->Checked)

{

float a=-1;

long double b=0;

int N=StrToInt(edtN->Text);

long double c=a+(b-a)/2;

long double ya=F(a);

long double yb=F(b);

long double yc=F(c);

long double x; x=T(a,b,c,ya,yb,yc);

long double yx=F(x);

для int i=1;i<=N-4;i++)

{

int fl=0;

if (x>c)fl=1;

if (x<c)fl=2;

if (x==c)fl=3;

switch (fl)

{

case 1:

{

if(yx>yc){b=x;yb=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);}

else if(yx<yc){a=c;ya=yc;c=x;yc=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);}

else if(yx==yc){a=c;ya=yc;b=x;yb=yx;c=(a+b)/2;yc=F(c);x=T(a,b,c,ya,yb,yc);yx=F(x);i++;}

}break;

case 2:

{

if(yx>yc){a=x;ya=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);}

else if(yx<yc){b=c;yb=yc;c=x;yc=yx;x=T(a,b,c,ya,yb,yc);yx=F(x);}

else if(yx==yc){a=x;ya=yx;b=c;yb=yc;c=(a+b)/2;yc=F(c);x=T(a,b,c,ya,yb,yc);yx=F(x);i++;}

}break;

case 3:{x=(a+c)/2;yx=F(x);}break;

}

}

edtE->Text=FloatToStr(fabs(b-a)/2);

edtX->Text=FloatToStr((b+a)/2);

}

}

void __fastcall TfrmMain::rbtn1Click(TObject *Sender)

{

edtD->Enabled=1;

btnBlockSize->Enabled=1;

}

void __fastcall TfrmMain::rbtn2Click(TObject *Sender)

{

edtD->Enabled=0;

btnBlockSize->Enabled=0;

}

void __fastcall TfrmMain::rbtn3Click(TObject *Sender)

{

edtD->Enabled=0;

btnBlockSize->Enabled=0;

}

void __fastcall TfrmMain::btnBlockSizeClick(TObject *Sender)

{

long double N=StrToInt(edtN->Text)-2;

long double i=2;

while((i<=N)&&(fmod(N,i)!=0)) i++;

edtD->Text=FloatToStr(i);

}

Тестирование: