Halcom 发表于 2017-3-16 23:07:10

基于粒子群算法PSO的极小值求解

#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<time.h>
#include<math.h>

/* PSO粒子群算法中的两个参数 */
#define c1 2         /* 学习因子1 */
#define c2 2         /* 学习因子2 */
#define w 4          /* 惯性权重*/
#define iter 150   /* 进化次数*/
#define sizepop 300    /* 种群规模*/
#define Vmax 1       /* 粒子速度上限 */
#define Vmin -1      /* 粒子速度下限 */
#define popmax 9   /* 粒子取值范围上限 */
#define popmin -9/* 粒子取值范围下限 */

#define length_data 1000   /* 预定义原始待分析数据长度 */

/* 适应度函数 */
double fun(double data[],int lineCount,double pop[])// 染色体的适应度
{
      // 输入:
               // data为原始数据 TOA TR Peo EUI
               // lineCount为数据的长度
               // pop 种群粒子个体
      // 输出:
               // 返回粒子对应的适应度值
      int i;   // 数组长度
      double C0,C1,C2,C3,C4,C5,C6,C7,C8,C9;                   /* 待优化求解未知量 */
      double EUI_pso,TOA,TR,Peo,EUI,Z,sum_Z=0;   // 原始数据,4组数据
      C0 = pop; C1 = pop;C2 = pop; C3 = pop; C4 = pop;
      C5 = pop; C6 = pop;C7 = pop; C8 = pop; C9 = pop;
//      leng = sizeof(data)/sizeof(data);                  // 数组的长度--行
//      printf("%lf\t%lf\n",C8,C9);         // 输出显示
      for(i=0;i<lineCount;i++)
      {
                TOA = data; TR = data; Peo = data; EUI = data;
      //      printf("%lf\n",TOA);
                EUI_pso = C0 +C1*TOA +C2*TR +C3*Peo +C4*TOA*TOA +C5*TR*TR +C6*Peo*Peo +C7*TR*Peo +C8*Peo*TOA +C9*TR*TOA;// PSO算法求解的EUI
                //printf("%lf\n",EUI_pso);
                Z= abs( EUI-EUI_pso );// 绝对误差和
                // printf("%lf\n",Z);
                sum_Z = sum_Z + Z;      // 叠加和
      }
//      printf("%lf\t\n",sum_Z);         // 输出显示
      
      return sum_Z;                  // 绝对误差和---适应度
      
}

void main(void)
{
      char path_excel[]="F:\\intercompilation\\C\\visual_stUdio_2010\\ysw_vs1\\ysw20140921_c++_3\\PSO3\\PSO3"; //
      FILE *fp;                                     // 文件
      double data,TOA,TR,Peo,EUI;   // 原始数据,4组数据
      int i,j,k,lineCount=0;                        // 上下标
      double rand_a,rand_a1,rand_a2,rand_a3;                   // 随机数
      double pop,V,fitness; // 初始化种群变量
      double bestfitness,zbest,gbest,fitnessgbest,fitnesszbest,Z;

      // 读取文本文件
      fp = fopen(strcat(path_excel,"\\data.txt"),"r");
      if(fp==NULL)
      {
                printf("fopen error!\n");
                return;
      }
      while(!feof(fp))// 判断获取的字符是否是文件的结束符
      {
                fscanf(fp,"%lf%lf%lf%lf",&TOA,&TR,&Peo,&EUI);
      //      printf("%lf\t%lf\t%lf\t%lf\n",TOA,TR,Peo,EUI);// 输出显示
                data = TOA;   data = TR;   
                data = Peo;   data = EUI;
      //      printf("%lf\t%lf\t%lf\t%lf\n",data,data,data,data);// 输出显示
                lineCount++;
         }
      srand(time(0)); // 初始化随机种子
      // 产生初始粒子和速度
      for(i=0;i<sizepop;i++)
      {
                // 随机产生一个种群
                for(j=0;j<10;j++)
                {
                        rand_a = 2.0*rand()/RAND_MAX-1; // 产生-1到1之间随机数
                //      printf("%lf\n",rand_a);         // 输出显示
                        pop = popmax*rand_a;      // 初始种群   C0-C9十个未知量
                //      printf("%lf\n",pop);
                        V = Vmax*rand_a;          // 初始化速度
                }
      }
      for(i=0;i<sizepop;i++)
      {
                // 计算适应度
                fitness = fun(data,lineCount-1,pop);   // 染色体的适应度
      //      printf("%lf\n",fitness);         // 输出显示
      }

      // 找最好的粒子个体--初始化
      bestfitness = fitness;         // 绝对误差和最小--初始化
      for(i=0;i<sizepop;i++)
      {
                for(j=0;j<10;j++)
                {
                        if(i==0)
                        {
                              zbest = pop;   // 全局最佳--初始化
                        }
                        gbest = pop;    // 个体最佳--初始化
                }
                fitnessgbest = fitness;   // 个体最佳适应度值--初始化
      }
      fitnesszbest = bestfitness;      // 全局最佳适应度值--初始化
      
      // 迭代寻优
      for(i=0;i<iter;i++)
      {
                for(j=0;j<sizepop;j++)
                {
                        // 速度更新
                        for(k=0;k<10;k++)
                        {
                              rand_a1 = rand()/RAND_MAX;   // 产生0到1之间随机数
                              rand_a2 = rand()/RAND_MAX;   // 产生0到1之间随机数
                              V = w*V + c1*rand_a1*(gbest - pop) + c2*rand_a2*(zbest - pop);
                              if(V>Vmax){V=Vmax;}// 速度上限
                              if(V<Vmin){V=Vmin;}// 速度下限
                              // 种群更新
                              pop = pop+0.5*V;
                              if(pop>popmax){pop=popmax;}// 种群取值上限
                              if(pop<popmin){pop=popmin;}// 种群取值下限
                        }
                        // 自适应变异
                        rand_a3 = rand()/RAND_MAX;   // 产生0到1之间随机数
                        if(rand_a3>0.8)
                        {
                              k=rand()%10;// 变异个体标号 0-9
                              pop = popmax*rand()/RAND_MAX;
                        }
                        // 适应度值data,lineCount-1,pop)
                        fitness=fun(data,lineCount-1,pop);
                        // 个体最优更新
                        if(fitness < fitnessgbest)
                        {
                              for(k=0;k<10;k++){ gbest = pop; }
                              fitnessgbest = fitness;
                        }
                        // 群体最优更新
                         if(fitness < fitnesszbest)
                         {
                                 for(k=0;k<10;k++){ zbest = pop; }
                                 fitnesszbest = fitness;
                         }
                }
                Z = fitnesszbest;// 存取最好适应度值

      }

      printf("最小绝对误差和值:%lf\n",Z);         // 最好适应度值输出显示
      printf("C0=%lf\tC1=%lf\tC2=%lf\tC3=%lf\tC4=%lf\n",zbest,zbest,zbest,zbest,zbest);   // C0-C4输出显示
      printf("C5=%lf\tC6=%lf\tC7=%lf\tC8=%lf\tC9=%lf\n",zbest,zbest,zbest,zbest,zbest);   // C5-C9输出显示

      printf("\n");// 输出显示
      fclose(fp);
      system("pause");    // 消除屏幕一闪即消失的情况
}
视频学习:链接:https://pan.baidu.com/s/132jBgG0JLVRAt-b4MM0I9w 密码:pa58

FIGHT 发表于 2020-5-8 11:38:36

我的多目标优化结果优于目标:'(
页: [1]
查看完整版本: 基于粒子群算法PSO的极小值求解