1 /*-------------------------------------------------------------*/
2 /*                            PSD-MADS                         */
3 /*-------------------------------------------------------------*/
4 /*                                                             */
5 /*  usage:                                                     */
6 /*                                                             */
7 /*    "mpirun -np p psdmads param_file bbe ns"                 */
8 /*    with p > 2, bbe > 0, and 1 <= ns <= number of variables  */
9 /*    . ns is the number of free variables for each process    */
10 /*    . bbe is the max number of evaluations for each process  */
11 /*                                                             */
12 /*-------------------------------------------------------------*/
13 /*                                                             */
14 /*  processes:                                                 */
15 /*                                                             */
16 /*            0: master                                        */
17 /*            1: pollster slave (1 direction)                  */
18 /*     2 to p-2: regular slaves (2ns directions)               */
19 /*          p-1: cache server                                  */
20 /*                                                             */
21 /*-------------------------------------------------------------*/
22 /*  See the user guide for other details and the description   */
23 /*  of the algorithm                                           */
24 /*-------------------------------------------------------------*/
25 
26 /*-----------------------------------------------------------*/
27 #include "Master_Slaves.hpp"
28 using namespace std;
29 using namespace NOMAD;
30 
31 const bool DEBUG = false;
32 
33 
34 
35 /*---------------------------------------------------*/
36 /*      The evaluator for G2_50 problem              */
37 /*---------------------------------------------------*/
38 class My_Evaluator : public NOMAD::Evaluator {
39 public:
My_Evaluator(const NOMAD::Parameters & p)40     My_Evaluator  ( const NOMAD::Parameters & p ) :
41     NOMAD::Evaluator ( p ) {}
42 
~My_Evaluator(void)43     ~My_Evaluator ( void ) {}
44 
eval_x(NOMAD::Eval_Point & x,const NOMAD::Double & h_max,bool & count_eval) const45     bool eval_x ( NOMAD::Eval_Point   & x          ,
46                  const NOMAD::Double & h_max      ,
47                  bool                & count_eval   ) const
48 	{
49 
50         int N=50;
51         long double sum1 = 0.0 , sum2 = 0.0 , sum3 = 0.0 , prod1 = 1.0 , prod2 = 1.0, g1=0, g2=0;
52         long double Xi;
53 
54         for (int i = 0 ; i < N ; i++ )
55         {
56 
57             Xi=x[i].value();
58 
59             sum1  += pow ( cos(Xi) , 4 );
60             sum2  += Xi;
61             sum3  += (i+1)*Xi*Xi;
62             prod1 *= pow ( cos(Xi) , 2 );
63             prod2 *= Xi;
64         }
65 
66 
67         g1 = -prod2+0.75;
68         g2 = sum2 -7.5*N;
69 
70         long double z  = - fabs ( ( sum1 - 2 * prod1 ) / sqrt(sum3) );
71 
72         x.set_bb_output  ( 0 , g1 ); // constraint 1
73         x.set_bb_output  ( 1 , g2 ); // constraint 2
74         x.set_bb_output  ( 2 , z  ); // objective value
75 
76 
77         count_eval = true; // count a black-box evaluation
78 
79 
80         return true;       // the evaluation succeeded
81 	}
82 
83 
84 };
85 
86 
87 
88 /*-----------------------------------*/
89 /*           main function           */
90 /*-----------------------------------*/
main(int argc,char ** argv)91 int main ( int argc , char ** argv ) {
92 
93     // MPI initialization:
94     MPI_Init ( &argc , &argv );
95     int rank , np;
96     MPI_Comm_rank ( MPI_COMM_WORLD, &rank );
97     MPI_Comm_size ( MPI_COMM_WORLD, &np   );
98 
99     // check the arguments and the number of processes:
100     if ( np <= 2 || argc != 4 ) {
101         if ( rank == 0 )
102             cerr << "usage: mpirun -np p " << argv[0]
103             << " param_file bbe ns, with p>2,"
104             << " bbe>1, and 1<=ns<=n."
105             << endl;
106         MPI_Finalize();
107         return 1;
108     }
109 
110     // display:
111     Display out ( cout );
112     out.precision ( 16 );
113 
114     // parameters:
115     NOMAD::Parameters p ( out );
116     int bbe = atoi ( argv[2] );
117     int ns  = atoi ( argv[3] );
118 
119     try {
120 
121         // read the parameters file:
122         p.read ( argv[1] );
123 
124         // This option is needed to have the same mesh index for all variables
125         p.set_ANISOTROPIC_MESH ( false );
126 
127         // check the parameters:
128         p.check();
129 
130 
131         if ( ns < 1 || ns > p.get_dimension() )
132             throw Exception ( __FILE__ , __LINE__ ,
133                              "Bad value for ns the number of free variables for each process" );
134 
135         if ( p.get_nb_obj() > 1 )
136             throw Exception ( __FILE__ , __LINE__ ,
137                              "PSD-MADS is not designed for multi-objective optimization" );
138     }
139     catch ( exception & e ) {
140         if ( rank == 0 )
141             cerr << "error with parameters" << endl;
142         MPI_Finalize();
143         return 1;
144     }
145 
146     // custom evaluator creation:
147     My_Evaluator ev   ( p );
148 
149     // start the master:
150     Master_Slaves master_slaves ( rank , np , bbe , ns , p , DEBUG ,ev);
151     master_slaves.start();
152 
153     // cache server:
154     Cache_Server cache ( out                  ,
155                         rank                 ,
156                         np                   ,
157                         p.get_h_min()        ,
158                         p.get_max_bb_eval()  ,
159                         false                ,  // ALLOW_MULTIPLE_EVALS
160                         DEBUG                  );
161 
162     // start the cache server:
163     if ( rank == np-1 ) {
164         if ( !DEBUG )
165             out << endl << "TIME\tBBE\tOBJ" << endl << endl;
166         cache.start();
167     }
168 
169     // slaves: algorithm creation and execution:
170     if ( rank != 0 && rank != np-1 ) {
171 
172         // MADS run:
173         master_slaves.mads_run ( cache );
174 
175         // stop the master:
176         master_slaves.stop();
177     }
178 
179     // stop the cache server:
180     cache.stop();
181 
182     // display the final solution:
183     if ( !DEBUG && rank == np-1 )
184         cache.display_best_points ( out );
185 
186     // MPI finalization:
187     MPI_Finalize();
188     return 0;
189 }
190