標(biāo)題:
差分進(jìn)化算法C++語(yǔ)言實(shí)現(xiàn)
[打印本頁(yè)]
作者:
pxdnh
時(shí)間:
2018-1-23 21:02
標(biāo)題:
差分進(jìn)化算法C++語(yǔ)言實(shí)現(xiàn)
差分進(jìn)化算法的C語(yǔ)言實(shí)現(xiàn),有大量的注釋,簡(jiǎn)單易懂!
/*DE_test
*對(duì)相應(yīng)的Matlab程序進(jìn)行測(cè)試
*/
#include <iostream>
#include <cmath>
#include <ctime>
using namespace std;
//產(chǎn)生隨機(jī)數(shù),隨機(jī)數(shù)為(0.0,1.0)
double Rand_Double(void)
{
return static_cast<double>(rand()) / static_cast<double>(RAND_MAX);
}
//測(cè)試函數(shù)Hansen
//參數(shù)個(gè)數(shù)為2
double Hansen(double *p_pars)
{
return ( cos(1.0) + 2.0*cos(p_pars[0]+2.0) + 3.0*cos(2.0*p_pars[0]+3.0)
+ 4.0*cos(3.0*p_pars[0]+4.0) + 5.0*cos(4.0*p_pars[0]+5.0) )
* ( cos(2.0*p_pars[1]+1.0) + 2.0*cos(3.0*p_pars[1]+2.0) +
3.0*cos(4.0*p_pars[1]+3.0) + 4.0*cos(5.0*p_pars[1]+4.0) + 5.0*cos(6.0*p_pars[1]+5.0) );
}
class CFunction
{
public:
void *m_p_fun;//指向測(cè)試函數(shù)的指針
int m_pars_num;//參數(shù)個(gè)數(shù)
double m_min;//下限
double m_max;//上限
bool m_pos;//求解最小值還是最大值,如果是最小值則m_pos為false,如果是最大值則m_pos為true
public:
CFunction(void *p_fun,int pars_num,double min,double max,bool pos)
:m_p_fun(p_fun),m_pars_num(pars_num),m_min(min),m_max(max),m_pos(pos)
{
}
virtual double Compute(double *p_pars) = 0;
};
class CHansen:public CFunction
{
public:
//注冊(cè)函數(shù)
CHansen(void)
:CFunction(Hansen,2,-10.0,10.0,false)
{
}
double Compute(double *p_pars)
{
return Hansen(p_pars);
}
};
//個(gè)體
class CIndividual
{
public:
double *m_p_DNA;//參數(shù)
double m_f;//適應(yīng)值
int m_DNA_length;//DNA的長(zhǎng)度
public:
CIndividual(void)
:m_f(0.0),m_DNA_length(0),m_p_DNA(NULL)
{
}
~CIndividual(void)
{
if(m_p_DNA!=NULL)
delete[] m_p_DNA;
}
//初始化,分配內(nèi)存空間
void Ini(int pars_num)
{
m_DNA_length = pars_num;
m_p_DNA = new double[m_DNA_length];
}
//假定兩者分配的內(nèi)存空間的大小一樣
CIndividual& operator=(CIndividual& ind)
{
m_f = ind.m_f;
//m_DNA_length = ind.m_DNA_length;
for(int i=0;i<m_DNA_length;++i)
{
m_p_DNA[i] = ind.m_p_DNA[i];
}
return *this;
}
friend ostream& operator<<(ostream& o,CIndividual& ind)
{
return o<<ind.m_f;
}
};
int main()
{
//---------------------------設(shè)置隨機(jī)數(shù)------------------------------------
srand((unsigned int)(time(NULL)));
//獲得參數(shù)
int Num,T;
double zoom,cr;
cout<<"種群大。";
cin>>Num;
cout<<"進(jìn)化代數(shù):";
cin>>T;
cout<<"縮放因子:";
cin>>zoom;
cout<<"交叉因子:";
cin>>cr;
//----------------------對(duì)函數(shù)進(jìn)行操作,注冊(cè)函數(shù)------------------------------
CHansen fun_Hansen;
CFunction *p_fun = &fun_Hansen;//為了實(shí)現(xiàn)多態(tài)
int pars_num = p_fun->m_pars_num;//參數(shù)個(gè)數(shù)
double min = p_fun->m_min;//下限
double max = p_fun->m_max;//上限
bool pos = p_fun->m_pos;//求最大值還是最小值
//----------------------注冊(cè)種群,并分配內(nèi)存空間-----------------------------
CIndividual *p_old = new CIndividual[Num];
CIndividual *p_new = new CIndividual[Num];
for(int i=0;i<Num;++i)
{
p_old[i].Ini(pars_num);
p_new[i].Ini(pars_num);
}
//-------------------------產(chǎn)生初始的隨機(jī)種群--------------------------------
for(int i=0;i<Num;++i)//對(duì)種群進(jìn)行遍歷
{
for(int j=0;j<pars_num;++j)//對(duì)參數(shù)列表進(jìn)行遍歷
p_old[i].m_p_DNA[j] = Rand_Double()*(max-min)+min;
p_old[i].m_f = p_fun->Compute(p_old[i].m_p_DNA);
}
CIndividual ind_best;
ind_best.Ini(pars_num);
for(int t=0;t<T;++t)//開始一代一代地進(jìn)化
{
//顯示結(jié)果
ind_best = p_old[0];
for(int i=1;i<Num;++i)
{
if(pos==true && ind_best.m_f<p_old[i].m_f)//求最大值
ind_best = p_old[i];
else if(pos==false && ind_best.m_f>p_old[i].m_f)//求最小值
ind_best = p_old[i];
}
cout<<ind_best<<"\n";
//差分變異
for(int i=0;i<Num;++i)//對(duì)種群進(jìn)行遍歷
{
//產(chǎn)生三個(gè)隨機(jī)數(shù)
int x1,x2,x3;
x1 = rand() % Num;
do
{
x2 = rand() % Num;
}while(x1==x2);
do
{
x3 = rand() % Num;
}while(x1==x3||x2==x3);
for(int j=0;j<pars_num;++j)//對(duì)參數(shù)列表進(jìn)行遍歷
{
p_new[i].m_p_DNA[j] = p_old[x1].m_p_DNA[j] + zoom * ( p_old[x2].m_p_DNA[j] - p_old[x3].m_p_DNA[j] );
if(p_new[i].m_p_DNA[j]<min || p_new[i].m_p_DNA[j]>max)//越界
p_new[i].m_p_DNA[j] = p_old[i].m_p_DNA[j];
}
}
//交叉操作,注意,交叉要對(duì)每個(gè)實(shí)數(shù)位進(jìn)行交叉
for(int i=0;i<Num;++i)//對(duì)種群進(jìn)行遍歷
{
for(int j=0;j<pars_num;++j)
{
if(Rand_Double()>cr)//不交叉
p_new[i].m_p_DNA[j] = p_old[i].m_p_DNA[j];
}
p_new[i].m_f = p_fun->Compute(p_new[i].m_p_DNA);
}
//選擇操作
for(int i=0;i<Num;++i)//對(duì)種群進(jìn)行遍歷
{
if(pos==true && p_new[i].m_f < p_old[i].m_f)//求最大值
p_new[i] = p_old[i];
else if(pos==false && p_new[i].m_f > p_old[i].m_f)//求最小值
p_new[i] = p_old[i];
}
//交換
CIndividual *p_tmp;
p_tmp = p_old;
p_old = p_new;
p_new = p_tmp;
//此時(shí),新種群的值被保存到p_old中
}
return 0;
}
復(fù)制代碼
Main.rar
2018-1-23 21:02 上傳
點(diǎn)擊文件名下載附件
下載積分: 黑幣 -5
1.79 KB, 下載次數(shù): 7, 下載積分: 黑幣 -5
歡迎光臨 (http://www.torrancerestoration.com/bbs/)
Powered by Discuz! X3.1