PaGMO  1.1.5
zdt.cpp
1 /*****************************************************************************
2  * Copyright (C) 2004-2015 The PaGMO development team, *
3  * Advanced Concepts Team (ACT), European Space Agency (ESA) *
4  * *
5  * https://github.com/esa/pagmo *
6  * *
7  * act@esa.int *
8  * *
9  * This program is free software; you can redistribute it and/or modify *
10  * it under the terms of the GNU General Public License as published by *
11  * the Free Software Foundation; either version 2 of the License, or *
12  * (at your option) any later version. *
13  * *
14  * This program is distributed in the hope that it will be useful, *
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of *
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
17  * GNU General Public License for more details. *
18  * *
19  * You should have received a copy of the GNU General Public License *
20  * along with this program; if not, write to the *
21  * Free Software Foundation, Inc., *
22  * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
23  *****************************************************************************/
24 
25 #include <cmath>
26 #include <boost/math/constants/constants.hpp>
27 
28 #include "../exceptions.h"
29 #include "../types.h"
30 #include "../population.h"
31 #include "zdt.h"
32 
33 static int __check__(int N)
34 {
35  if (N > 6 || N < 1) {
36  pagmo_throw(value_error, "the problem id needs to be one of [1..6]");
37  }
38  return N;
39 }
40 
41 namespace pagmo { namespace problem {
42 
51  :base_unc_mo( (__check__(id) != 5) ? param_1 : 30 + 5 * (param_1 - 1), (__check__(id) != 5) ? 0 : 30 + 5 * (param_1 - 1), 2 ),
52  m_problem_number(__check__(id))
53 {
54  if(param_1 <= 0) {
55  pagmo_throw(value_error,"Invalid parameter (problem dimension needs to be higher)");
56  }
57 
58  // set the bounds for the current problem
59  switch(m_problem_number)
60  {
61  case 1:
62  case 2:
63  case 3:
64  case 6:
65  {
66  set_lb(0.0);
67  set_ub(1.0);
68  break;
69  }
70  case 4:
71  {
72  set_lb(-5.0);
73  set_ub(5.0);
74  set_lb(0,0.0);
75  set_ub(0,1.0);
76  break;
77  }
78  case 5:
79  {
80  set_lb(0);
81  set_ub(1);
82  break;
83  }
84  default:
85  pagmo_throw(value_error, "Error: There are only 6 test functions in this test suite!");
86  break;
87  }
88 }
89 
92 {
93  return base_ptr(new zdt(*this));
94 }
95 
98 {
99  switch(m_problem_number)
100  {
101  case 1:
102  case 2:
103  case 3:
104  return g0123_convergence_metric(x);
105  case 4:
106  return g04_convergence_metric(x);
107  case 5:
108  return g05_convergence_metric(x);
109  case 6:
110  return g06_convergence_metric(x);
111  default:
112  pagmo_throw(value_error, "Error: There are only 6 test functions in this test suite!");
113  }
114  return -1.0;
115 }
116 
119 {
120  switch(m_problem_number)
121  {
122  case 1:
123  g01_objfun_impl(f,x);
124  break;
125  case 2:
126  g02_objfun_impl(f,x);
127  break;
128  case 3:
129  g03_objfun_impl(f,x);
130  break;
131  case 4:
132  g04_objfun_impl(f,x);
133  break;
134  case 5:
135  g05_objfun_impl(f,x);
136  break;
137  case 6:
138  g06_objfun_impl(f,x);
139  break;
140  default:
141  pagmo_throw(value_error, "Error: There are only 6 test functions in this test suite!");
142  break;
143  }
144 }
145 
146 // shared convergence metric for ZDT1, ZDT2 and ZDT3
147 double zdt::g0123_convergence_metric(const decision_vector &x) const
148 {
149  double c = 0.0;
150  double g = 0.0;
151 
152  for(problem::base::size_type j = 1; j < x.size(); ++j) {
153  g += x[j];
154  }
155  c += 1 + (9 * g) / (x.size()-1);
156  return c - 1;
157 }
158 
159 void zdt::g01_objfun_impl(fitness_vector &f, const decision_vector &x) const
160 {
161  pagmo_assert(f.size() == 2);
162  pagmo_assert(x.size() == get_dimension());
163 
164  double g = 0;
165 
166  f[0] = x[0];
167 
168  for(problem::base::size_type i = 1; i < x.size(); ++i) {
169  g += x[i];
170  }
171  g = 1 + (9 * g) / (x.size()-1);
172 
173  f[1] = g * ( 1 - sqrt(x[0]/g));
174 
175 }
176 
177 void zdt::g02_objfun_impl(fitness_vector &f, const decision_vector &x) const
178 {
179  pagmo_assert(f.size() == 2);
180  pagmo_assert(x.size() == get_dimension());
181 
182  double g = 0;
183 
184  f[0] = x[0];
185 
186  for(problem::base::size_type i = 1; i < x.size(); ++i) {
187  g += x[i];
188  }
189  g = 1 + (9 * g) / (x.size() - 1);
190 
191  f[1] = g * ( 1 - (x[0]/g)*(x[0]/g));
192 }
193 
194 void zdt::g03_objfun_impl(fitness_vector &f, const decision_vector &x) const
195 {
196  pagmo_assert(f.size() == 2);
197  pagmo_assert(x.size() == get_dimension());
198 
199  double g = 0;
200 
201  f[0] = x[0];
202 
203  for(problem::base::size_type i = 1; i < x.size(); ++i) {
204  g += x[i];
205  }
206  g = 1 + (9 * g) / (x.size()-1);
207 
208  f[1] = g * ( 1 - sqrt(x[0]/g) - x[0]/g * sin(10 * boost::math::constants::pi<double>() * x[0]));
209 
210 }
211 
212 double zdt::g04_convergence_metric(const decision_vector &x) const
213 {
214  double c = 0.0;
215  double g = 0.0;
216 
217  for(problem::base::size_type j = 1; j < x.size(); ++j) {
218  g += x[j]*x[j] - 10 * cos(4 * boost::math::constants::pi<double>() * x[j]);
219  }
220  c += 1 + 10 * (x.size()-1) + g;
221  return c - 1;
222 }
223 
224 // ZDT4': lambda x: 1 + 10 * (len(x) - 1) + sum([xi**2 - 10*np.cos(4*np.pi*xi) for xi in x[1:]])
225 void zdt::g04_objfun_impl(fitness_vector &f, const decision_vector &x) const
226 {
227  pagmo_assert(f.size() == 2);
228  pagmo_assert(x.size() == get_dimension());
229 
230  double g = 1 + 10 * (x.size() - 1);
231 
232  f[0] = x[0];
233 
234  for(problem::base::size_type i = 1; i < x.size(); ++i) {
235  g += x[i]*x[i] - 10 * cos(4 * boost::math::constants::pi<double>() * x[i]);
236  }
237 
238  f[1] = g * ( 1 - sqrt(x[0]/g) );
239 
240 }
241 
242 
243 double zdt::g05_convergence_metric(const decision_vector &x) const
244 {
245  double c = 0.0;
246  double g = 0.0;
247  int k = 30;
248 
249  problem::base::size_type n_vectors = ((x.size()-30)/5) + 1;
250  std::vector<int> u(n_vectors,0);
251  std::vector<int> v(n_vectors);
252 
253  for (problem::base::size_type i=1; i<n_vectors; i++)
254  {
255  for (int j=0; j<5; j++)
256  {
257  if (x[k] == 1)
258  {
259  u[i]++;
260  }
261  k++;
262  }
263  }
264 
265  for (problem::base::size_type i=1; i<n_vectors; i++)
266  {
267  if (u[i] < 5)
268  {
269  v[i] = 2 + u[i];
270  }
271  else
272  {
273  v[i] = 1;
274  }
275  }
276 
277  for (problem::base::size_type i=1; i<n_vectors; i++)
278  {
279  g += v[i];
280  }
281  c += g;
282  return c - n_vectors + 1;
283 }
284 
285 void zdt::g05_objfun_impl(fitness_vector &f, const decision_vector &x) const
286 {
287  pagmo_assert(f.size() == 2);
288  pagmo_assert(x.size() == get_dimension());
289  double g = 0;
290  problem::base::size_type size_x = x.size();
291  problem::base::size_type n_vectors = ((size_x-30)/5) + 1;
292  int j, k = 30;
293  std::vector<int> u(n_vectors);
294  std::vector<int> v(n_vectors);
295 
296 
297  for (problem::base::size_type i=0; i<n_vectors; i++)
298  {
299  u[i] = 0;
300  }
301  for (j=0; j<30; j++)
302  {
303  if (x[j] == 1)
304  {
305  u[0]++;
306  }
307  }
308  for (problem::base::size_type i=1; i<n_vectors; i++)
309  {
310  for (j=0; j<5; j++)
311  {
312  if (x[k] == 1)
313  {
314  u[i]++;
315  }
316  k++;
317  }
318  }
319  f[0] = 1.0 + u[0];
320  for (problem::base::size_type i=1; i<n_vectors; i++)
321  {
322  if (u[i] < 5)
323  {
324  v[i] = 2 + u[i];
325  }
326  else
327  {
328  v[i] = 1;
329  }
330  }
331  g = 0;
332  for (problem::base::size_type i=1; i<n_vectors; i++)
333  {
334  g += v[i];
335  }
336 
337  f[1] = g * (1.0/f[0]);
338 
339 
340 }
341 
342 double zdt::g06_convergence_metric(const decision_vector &x) const
343 {
344  double c = 0.0;
345  double g = 0.0;
346 
347  for(problem::base::size_type j = 1; j < x.size(); ++j) {
348  g += x[j];
349  }
350  c += 1 + 9 * pow((g / (x.size()-1)),0.25);
351 
352  return c - 1;
353 }
354 
355 
356 void zdt::g06_objfun_impl(fitness_vector &f, const decision_vector &x) const
357 {
358  pagmo_assert(f.size() == 2);
359  pagmo_assert(x.size() == get_dimension());
360 
361  double g = 0;
362 
363  f[0] = 1 - exp(-4*x[0])*pow(sin(6*boost::math::constants::pi<double>()*x[0]),6);
364 
365  for(problem::base::size_type i = 1; i < x.size(); ++i) {
366  g += x[i];
367  }
368  g = 1 + 9 * pow((g/(x.size()-1)),0.25);
369 
370  f[1] = g * ( 1 - (f[0]/g)*(f[0]/g));
371 
372 }
373 
374 
375 std::string zdt::get_name() const
376 {
377  std::string retval("ZDT");
378  retval.append(boost::lexical_cast<std::string>(m_problem_number));
379 
380  return retval;
381 }
382 
383 }}
384 
385 BOOST_CLASS_EXPORT_IMPLEMENT(pagmo::problem::zdt)
Root PaGMO namespace.
base_ptr clone() const
Clone method.
Definition: zdt.cpp:91
boost::shared_ptr< base > base_ptr
Alias for shared pointer to base problem.
Definition: problem/base.h:62
std::vector< double > decision_vector
Decision vector type.
Definition: types.h:40
size_type get_dimension() const
Return global dimension.
void set_lb(const decision_vector &)
Set lower bounds from pagmo::decision_vector.
zdt(size_type=1, size_type=30)
Definition: zdt.cpp:50
Base Class for Unconstrained Multi-objective problems.
Definition: base_unc_mo.h:47
std::string get_name() const
Get problem's name.
Definition: zdt.cpp:375
void set_ub(const decision_vector &)
Set upper bounds from pagmo::decision_vector.
std::vector< double > fitness_vector
Fitness vector type.
Definition: types.h:42
double convergence_metric(const decision_vector &) const
Convergence metric for a decision_vector (0 = converged to the optimal front)
Definition: zdt.cpp:97
void objfun_impl(fitness_vector &, const decision_vector &) const
Implementation of the objective function.
Definition: zdt.cpp:118
decision_vector::size_type size_type
Problem's size type: the same as pagmo::decision_vector's size type.
Definition: problem/base.h:160
ZDT problem test suite.
Definition: zdt.h:134