openGPMP
Open Source Mathematics Package
Public Member Functions | Private Member Functions | List of all members
gpmp::optim::Func Class Reference

A class containing various utility functions and optimization methods. More...

#include <function.hpp>

Public Member Functions

std::vector< double > generate_random_point (const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds) const
 Generates a random point within specified bounds. More...
 
std::vector< double > generate_fibonacci_sequence (size_t length) const
 Generates a Fibonacci sequence up to a specified length. More...
 
std::vector< double > vector_addition (const std::vector< double > &a, const std::vector< double > &b) const
 Performs vector addition. More...
 
std::vector< double > vector_subtraction (const std::vector< double > &a, const std::vector< double > &b) const
 Performs vector subtraction. More...
 
std::vector< double > vector_scalar_multiply (double scalar, const std::vector< double > &vec) const
 Performs vector scalar multiplication. More...
 
double calculate_midpoint (double a, double b, double fraction) const
 Calculates the midpoint between two values. More...
 
double golden_section_search (const std::function< double(double)> &func, double a, double b, double tol)
 Finds the minimum of a univariate function using Golden-section search. More...
 
double linear_interpolation (double x, double x0, double x1, double y0, double y1)
 Interpolates a univariate function using linear interpolation. More...
 
double cubic_interpolation (double x, double x0, double x1, double y0, double y1, double y0_prime, double y1_prime)
 Interpolates a univariate function using cubic interpolation. More...
 
std::vector< double > golden_section_search_multivariate (const std::function< double(const std::vector< double > &)> &func, const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds, double tol)
 Finds the minimum of a multivariate function using Golden-section search. More...
 
double random_search (const std::function< double(const std::vector< double > &)> &func, const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds, size_t max_iterations)
 Performs random search for function optimization. More...
 
std::vector< double > fit_linear (const std::vector< double > &x, const std::vector< double > &y)
 Fits a linear function to given data points. More...
 
double fibonacci_search (const std::function< double(const std::vector< double > &)> &func, const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds, size_t max_iterations)
 Performs Fibonacci search for function optimization. More...
 
double ternary_search (const std::function< double(const std::vector< double > &)> &func, const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds, size_t max_iterations) const
 Performs ternary search for function optimization. More...
 
std::vector< double > bisection_method (const std::function< double(const std::vector< double > &)> &func, double lower_bound, double upper_bound, size_t max_iterations)
 Performs the bisection method for function optimization. More...
 
std::vector< double > newton_method (const std::function< double(const std::vector< double > &)> &func, const std::function< double(const std::vector< double > &)> &derivative, double initial_guess, size_t max_iterations)
 Performs Newton's method for function optimization. More...
 
std::vector< double > regula_falsi (const std::function< double(const std::vector< double > &)> &func, double lower_bound, double upper_bound, size_t max_iterations)
 Performs Regula Falsi (False Position) method for function optimization. More...
 
std::vector< double > cubic_fit (const std::vector< double > &x, const std::vector< double > &y)
 Fits a cubic function to given data points. More...
 
std::vector< double > nelder_mead (const std::function< double(const std::vector< double > &)> &func, std::vector< double > initial_point, double tolerance, size_t max_iterations)
 Finds the minimum of a multivariate function using the Nelder–Mead method. More...
 
std::vector< double > calculate_centroid (const std::vector< std::vector< double >> &simplex, size_t exclude_index)
 Calculates the centroid of a simplex excluding a specific point. More...
 
std::vector< double > reflect (const std::vector< double > &point, const std::vector< double > &centroid, double reflection_coefficient)
 Reflects a point with respect to a centroid. More...
 
double calculate_range (const std::vector< double > &values)
 Calculates the range of values. More...
 
bool is_valid_interval (double a, double b)
 Checks if a given interval is valid (lower bound < upper bound) More...
 

Private Member Functions

double golden_section_search_minimize (const std::function< double(double)> &func, double a, double b, double tol, double x1, double x2)
 Finds the minimum of a univariate function using Golden-section search (Internal helper function) More...
 
std::vector< double > golden_section_search_minimize_multivariate (const std::function< double(const std::vector< double > &)> &func, const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds, double tol, const std::vector< double > &x1, const std::vector< double > &x2)
 Finds the minimum of a multivariate function using Golden-section search (Internal helper function) More...
 

Detailed Description

A class containing various utility functions and optimization methods.

Definition at line 49 of file function.hpp.

Member Function Documentation

◆ bisection_method()

std::vector< double > gpmp::optim::Func::bisection_method ( const std::function< double(const std::vector< double > &)> &  func,
double  lower_bound,
double  upper_bound,
size_t  max_iterations 
)

Performs the bisection method for function optimization.

Parameters
funcThe univariate function to optimize
lower_boundThe lower bound of the search interval
upper_boundThe upper bound of the search interval
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 362 of file function.cpp.

366  {
367  if (lower_bound >= upper_bound) {
368  throw std::invalid_argument("Invalid bounds for bisection method.");
369  }
370 
371  double a = lower_bound;
372  double b = upper_bound;
373 
374  for (size_t iteration = 0; iteration < max_iterations; ++iteration) {
375  double midpoint = (a + b) / 2.0;
376 
377  // if (func({midpoint}) == 0.0) {
378  if (fabs(func({midpoint}) - 0.0f) <
379  std::numeric_limits<double>::epsilon()) {
380  return {midpoint};
381  } else if (func({midpoint}) * func({a}) < 0) {
382  b = midpoint;
383  } else {
384  a = midpoint;
385  }
386  }
387 
388  return {(a + b) / 2.0};
389 }

◆ calculate_centroid()

std::vector< double > gpmp::optim::Func::calculate_centroid ( const std::vector< std::vector< double >> &  simplex,
size_t  exclude_index 
)

Calculates the centroid of a simplex excluding a specific point.

Parameters
simplexThe simplex
exclude_indexThe index of the point to exclude
Returns
The centroid of the simplex

Definition at line 606 of file function.cpp.

608  {
609  size_t n = simplex[0].size();
610  std::vector<double> centroid(n, 0.0);
611 
612  for (size_t i = 0; i < simplex.size(); ++i) {
613  if (i != exclude_index) {
614  for (size_t j = 0; j < n; ++j) {
615  centroid[j] += simplex[i][j];
616  }
617  }
618  }
619 
620  for (size_t j = 0; j < n; ++j) {
621  centroid[j] /= (simplex.size() - 1);
622  }
623 
624  return centroid;
625 }

◆ calculate_midpoint()

double gpmp::optim::Func::calculate_midpoint ( double  a,
double  b,
double  fraction 
) const

Calculates the midpoint between two values.

Parameters
aThe first value
bThe second value
fractionThe fraction determining the midpoint
Returns
The midpoint between a and b

Definition at line 116 of file function.cpp.

118  {
119  return a + fraction * (b - a);
120 }

◆ calculate_range()

double gpmp::optim::Func::calculate_range ( const std::vector< double > &  values)

Calculates the range of values.

Parameters
valuesThe vector of values
Returns
The range of values

Definition at line 642 of file function.cpp.

642  {
643  double max_value = *std::max_element(values.begin(), values.end());
644  double min_value = *std::min_element(values.begin(), values.end());
645 
646  return max_value - min_value;
647 }

◆ cubic_fit()

std::vector< double > gpmp::optim::Func::cubic_fit ( const std::vector< double > &  x,
const std::vector< double > &  y 
)

Fits a cubic function to given data points.

Parameters
xThe x-coordinates of data points
yThe corresponding y-coordinates of data points
Returns
Coefficients of the cubic fit

Definition at line 449 of file function.cpp.

450  {
451  size_t n = x.size();
452 
453  if (n != y.size() || n < 4) {
454  throw std::invalid_argument(
455  "Invalid input dimensions for cubic curve fitting.");
456  }
457 
458  double sum_x = 0.0, sum_y = 0.0, sum_x_squared = 0.0, sum_x_cubed = 0.0,
459  sum_xy = 0.0, sum_x_squared_y = 0.0, sum_squared = 0.0;
460 
461  for (size_t i = 0; i < n; ++i) {
462  double xi_squared = x[i] * x[i];
463  double xi_cubed = xi_squared * x[i];
464 
465  sum_x += x[i];
466  sum_y += y[i];
467  sum_x_squared += xi_squared;
468  sum_x_cubed += xi_cubed;
469  sum_xy += x[i] * y[i];
470  sum_x_squared_y += xi_squared * y[i];
471  }
472 
473  double determinant = n * sum_x_squared * sum_x_squared * sum_x_squared -
474  sum_x_squared * sum_x_squared * sum_x * sum_x_squared -
475  sum_x * sum_x * sum_x_squared * sum_x_squared +
476  sum_x_squared * sum_x * sum_x * sum_x_squared +
477  sum_x * sum_x * sum_x * sum_x_squared -
478  n * sum_x * sum_x * sum_x * sum_x;
479 
480  double a = (n * sum_x_squared * sum_x_squared_y -
481  sum_x_squared * sum_x * sum_xy * sum_x_squared -
482  sum_x * sum_x_squared_y * sum_x_squared +
483  sum_x_squared * sum_x * sum_x * sum_xy +
484  sum_x * sum_x * sum_x_squared * sum_x * sum_y -
485  n * sum_x * sum_x * sum_x * sum_xy) /
486  determinant;
487 
488  double b = (n * sum_x_squared * sum_x_squared * sum_xy -
489  sum_x_squared_y * sum_x_squared * sum_x_squared +
490  sum_x * sum_x * sum_x_squared_y * sum_x_squared -
491  sum_x_squared * sum_x * sum_x * sum_x * sum_xy -
492  sum_x_squared * sum_x_squared * sum_x * sum_y +
493  n * sum_x * sum_x * sum_x * sum_x * sum_xy) /
494  determinant;
495 
496  double c =
497  (n * sum_x_squared * sum_x_squared * sum_x * sum_xy -
498  sum_x_squared * sum_x_squared_y * sum_x_squared * sum_x +
499  sum_x * sum_x * sum_x_squared_y * sum_x_squared * sum_x_squared -
500  sum_x_squared * sum_x * sum_x * sum_x * sum_x_squared -
501  sum_x * sum_x_squared * sum_x_squared * sum_x * sum_y +
502  n * sum_x * sum_x * sum_x * sum_squared * sum_x * sum_y) /
503  determinant;
504 
505  double d =
506  (n * sum_x_squared * sum_x_squared * sum_x * sum_x * sum_xy -
507  sum_x_squared * sum_x_squared_y * sum_x_squared * sum_x_squared *
508  sum_x +
509  sum_x_squared * sum_x * sum_x_squared_y * sum_x_squared *
510  sum_x_squared -
511  sum_x_squared * sum_x * sum_x * sum_x * sum_x_squared -
512  sum_x * sum_x_squared * sum_x_squared * sum_x * sum_x_squared +
513  n * sum_x * sum_x * sum_x * sum_squared * sum_x * sum_x_squared) /
514  determinant;
515 
516  return {a, b, c, d};
517 }

◆ cubic_interpolation()

double gpmp::optim::Func::cubic_interpolation ( double  x,
double  x0,
double  x1,
double  y0,
double  y1,
double  y0_prime,
double  y1_prime 
)

Interpolates a univariate function using cubic interpolation.

Parameters
xThe point at which to interpolate
x0The left point of the interval
x1The right point of the interval
y0The function value at x0
y1The function value at x1
y0_primeThe derivative value at x0
y1_primeThe derivative value at x1
Returns
The interpolated function value at x

Definition at line 147 of file function.cpp.

153  {
154  double h = x1 - x0;
155  double t = (x - x0) / h;
156  double t2 = t * t;
157  double t3 = t2 * t;
158 
159  double a = 2 * t3 - 3 * t2 + 1;
160  double b = t3 - 2 * t2 + t;
161  double c = t3 - t2;
162  double d = -2 * t3 + 3 * t2;
163 
164  return a * y0 + b * (h * y0_prime) + c * (h * y1_prime) + d * y1;
165 }

◆ fibonacci_search()

double gpmp::optim::Func::fibonacci_search ( const std::function< double(const std::vector< double > &)> &  func,
const std::vector< double > &  lower_bounds,
const std::vector< double > &  upper_bounds,
size_t  max_iterations 
)

Performs Fibonacci search for function optimization.

Parameters
funcThe multivariate function to optimize
lower_boundsThe lower bounds of the search interval
upper_boundsThe upper bounds of the search interval
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 289 of file function.cpp.

293  {
294 
295  if (lower_bounds.size() != upper_bounds.size()) {
296  throw std::invalid_argument(
297  "Lower and upper bounds must have the same dimension.");
298  }
299 
300  size_t dimension = lower_bounds.size();
301  std::vector<double> fib_sequence = generate_fibonacci_sequence(
302  max_iterations + 2); // Adjusted for proper Fibonacci generation
303 
304  // Print Fibonacci sequence for debugging
305  std::vector<double> a = lower_bounds;
306  std::vector<double> b = upper_bounds;
307 
308  for (size_t k = 0; k < max_iterations; ++k) {
309  double lambda = (fib_sequence[max_iterations - k + 1] /
310  fib_sequence[max_iterations - k +
311  2]); // Corrected lambda calculation
312 
313  std::vector<double> x1(dimension);
314  std::vector<double> x2(dimension);
315 
316  for (size_t i = 0; i < dimension; ++i) {
317  x1[i] = a[i] + lambda * (b[i] - a[i]);
318  x2[i] = b[i] + lambda * (a[i] - b[i]);
319  }
320 
321  if (func(x1) < func(x2)) {
322  b = x2;
323  } else {
324  a = x1;
325  }
326  }
327 
328  return func(a);
329 }
std::vector< double > generate_fibonacci_sequence(size_t length) const
Generates a Fibonacci sequence up to a specified length.
Definition: function.cpp:57

◆ fit_linear()

std::vector< double > gpmp::optim::Func::fit_linear ( const std::vector< double > &  x,
const std::vector< double > &  y 
)

Fits a linear function to given data points.

Parameters
xThe x-coordinates of data points
yThe corresponding y-coordinates of data points
Returns
Coefficients of the linear fit

Definition at line 264 of file function.cpp.

265  {
266  size_t n = x.size();
267 
268  if (n != y.size() || n < 2) {
269  throw std::invalid_argument(
270  "Invalid input dimensions for linear curve fitting.");
271  }
272 
273  double sum_x = 0.0, sum_y = 0.0, sum_xy = 0.0, sum_x_squared = 0.0;
274 
275  for (size_t i = 0; i < n; ++i) {
276  sum_x += x[i];
277  sum_y += y[i];
278  sum_xy += x[i] * y[i];
279  sum_x_squared += x[i] * x[i];
280  }
281 
282  double a =
283  (n * sum_xy - sum_x * sum_y) / (n * sum_x_squared - sum_x * sum_x);
284  double b = (sum_y - a * sum_x) / n;
285 
286  return {a, b};
287 }

◆ generate_fibonacci_sequence()

std::vector< double > gpmp::optim::Func::generate_fibonacci_sequence ( size_t  length) const

Generates a Fibonacci sequence up to a specified length.

Parameters
lengthThe length of the Fibonacci sequence
Returns
The Fibonacci sequence

Definition at line 57 of file function.cpp.

57  {
58  std::vector<double> sequence;
59 
60  // double golden_ratio = (1.0 + std::sqrt(5.0)) / 2.0;
61  double fibonacci_prev = 0.0;
62  double fibonacci_curr = 1.0;
63  for (size_t i = 0; i < length; ++i) {
64  sequence.push_back(fibonacci_prev);
65  double fibonacci_next = fibonacci_curr + fibonacci_prev;
66  fibonacci_prev = fibonacci_curr;
67  fibonacci_curr = fibonacci_next;
68  }
69 
70  return sequence;
71 }

◆ generate_random_point()

std::vector< double > gpmp::optim::Func::generate_random_point ( const std::vector< double > &  lower_bounds,
const std::vector< double > &  upper_bounds 
) const

Generates a random point within specified bounds.

Parameters
lower_boundsThe lower bounds for each dimension
upper_boundsThe upper bounds for each dimension
Returns
A randomly generated point within the specified bounds

Definition at line 37 of file function.cpp.

39  {
40  if (lower_bounds.size() != upper_bounds.size()) {
41  throw std::invalid_argument(
42  "Lower and upper bounds must have the same dimension.");
43  }
44 
45  std::vector<double> point;
46  for (size_t i = 0; i < lower_bounds.size(); ++i) {
47  double random_value =
48  lower_bounds[i] + static_cast<double>(rand()) / RAND_MAX *
49  (upper_bounds[i] - lower_bounds[i]);
50  point.push_back(random_value);
51  }
52 
53  return point;
54 }

◆ golden_section_search()

double gpmp::optim::Func::golden_section_search ( const std::function< double(double)> &  func,
double  a,
double  b,
double  tol 
)

Finds the minimum of a univariate function using Golden-section search.

Parameters
funcThe univariate function to minimize
aThe lower bound of the search interval
bThe upper bound of the search interval
tolThe tolerance for stopping criterion
Returns
The value of the argument that minimizes the function

Definition at line 122 of file function.cpp.

126  {
127  if (!is_valid_interval(a, b)) {
128  throw std::invalid_argument(
129  "Invalid interval: lower bound must be less than upper bound.");
130  }
131 
132  const double inv_phi = (std::sqrt(5.0) - 1.0) / 2.0;
133  double x1 = b - inv_phi * (b - a);
134  double x2 = a + inv_phi * (b - a);
135 
136  return golden_section_search_minimize(func, a, b, tol, x1, x2);
137 }
bool is_valid_interval(double a, double b)
Checks if a given interval is valid (lower bound < upper bound)
Definition: function.cpp:690
double golden_section_search_minimize(const std::function< double(double)> &func, double a, double b, double tol, double x1, double x2)
Finds the minimum of a univariate function using Golden-section search (Internal helper function)
Definition: function.cpp:167

◆ golden_section_search_minimize()

double gpmp::optim::Func::golden_section_search_minimize ( const std::function< double(double)> &  func,
double  a,
double  b,
double  tol,
double  x1,
double  x2 
)
private

Finds the minimum of a univariate function using Golden-section search (Internal helper function)

Parameters
funcThe univariate function to minimize
aThe lower bound of the search interval
bThe upper bound of the search interval
tolThe tolerance for stopping criterion
x1Internal helper parameter
x2Internal helper parameter
Returns
The value of the argument that minimizes the function

Definition at line 167 of file function.cpp.

173  {
174  double f1 = func(x1);
175  double f2 = func(x2);
176 
177  while ((b - a) > tol) {
178  if (f1 < f2) {
179  b = x2;
180  x2 = x1;
181  x1 = a + b - x2;
182  f2 = f1;
183  f1 = func(x1);
184  } else {
185  a = x1;
186  x1 = x2;
187  x2 = a + b - x1;
188  f1 = f2;
189  f2 = func(x2);
190  }
191  }
192 
193  return (f1 < f2) ? x1 : x2;
194 }

◆ golden_section_search_minimize_multivariate()

std::vector< double > gpmp::optim::Func::golden_section_search_minimize_multivariate ( const std::function< double(const std::vector< double > &)> &  func,
const std::vector< double > &  lower_bounds,
const std::vector< double > &  upper_bounds,
double  tol,
const std::vector< double > &  x1,
const std::vector< double > &  x2 
)
private

Finds the minimum of a multivariate function using Golden-section search (Internal helper function)

Parameters
funcThe multivariate function to minimize
lower_boundsThe lower bounds of the search interval
upper_boundsThe upper bounds of the search interval
tolThe tolerance for stopping criterion
x1Internal helper parameter
x2Internal helper parameter
Returns
The vector of arguments that minimizes the function

Definition at line 650 of file function.cpp.

656  {
657 
658  std::vector<double> best_point;
659  double best_value = std::numeric_limits<double>::infinity();
660 
661  // Perform golden section search for each dimension
662  for (size_t i = 0; i < lower_bounds.size(); ++i) {
663  double a = lower_bounds[i];
664  double b = upper_bounds[i];
665  double x1_i = x1[i];
666  double x2_i = x2[i];
667 
668  double result = golden_section_search_minimize(
669  [&](double t) {
670  std::vector<double> point(x1);
671  point[i] = calculate_midpoint(x1_i, x2_i, t);
672  return func(point);
673  },
674  a,
675  b,
676  tol,
677  0.382,
678  0.618);
679 
680  if (result < best_value) {
681  best_value = result;
682  best_point = x1;
683  best_point[i] = calculate_midpoint(x1_i, x2_i, result);
684  }
685  }
686 
687  return best_point;
688 }
double calculate_midpoint(double a, double b, double fraction) const
Calculates the midpoint between two values.
Definition: function.cpp:116

◆ golden_section_search_multivariate()

std::vector< double > gpmp::optim::Func::golden_section_search_multivariate ( const std::function< double(const std::vector< double > &)> &  func,
const std::vector< double > &  lower_bounds,
const std::vector< double > &  upper_bounds,
double  tol 
)

Finds the minimum of a multivariate function using Golden-section search.

Parameters
funcThe multivariate function to minimize
lower_boundsThe lower bounds of the search interval
upper_boundsThe upper bounds of the search interval
tolThe tolerance for stopping criterion
Returns
The vector of arguments that minimizes the function

Definition at line 200 of file function.cpp.

204  {
205  if (lower_bounds.size() != upper_bounds.size()) {
206  throw std::invalid_argument(
207  "Lower and upper bounds must have the same dimension.");
208  }
209 
210  // Initialize x1 and x2 based on the golden section ratio for each dimension
211  std::vector<double> x1(lower_bounds.size());
212  std::vector<double> x2(lower_bounds.size());
213 
214  for (size_t i = 0; i < lower_bounds.size(); ++i) {
215  if (!is_valid_interval(lower_bounds[i], upper_bounds[i])) {
216  throw std::invalid_argument("Invalid interval for dimension " +
217  std::to_string(i));
218  }
219 
220  const double inv_phi = (std::sqrt(5.0) - 1.0) / 2.0;
221  x1[i] = upper_bounds[i] - inv_phi * (upper_bounds[i] - lower_bounds[i]);
222  x2[i] = lower_bounds[i] + inv_phi * (upper_bounds[i] - lower_bounds[i]);
223  }
224 
226  lower_bounds,
227  upper_bounds,
228  tol,
229  x1,
230  x2);
231 }
std::vector< double > golden_section_search_minimize_multivariate(const std::function< double(const std::vector< double > &)> &func, const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds, double tol, const std::vector< double > &x1, const std::vector< double > &x2)
Finds the minimum of a multivariate function using Golden-section search (Internal helper function)
Definition: function.cpp:650

◆ is_valid_interval()

bool gpmp::optim::Func::is_valid_interval ( double  a,
double  b 
)

Checks if a given interval is valid (lower bound < upper bound)

Parameters
aThe lower bound of the interval
bThe upper bound of the interval
Returns
True if the interval is valid, false otherwise

Definition at line 690 of file function.cpp.

690  {
691  return a < b;
692 }

◆ linear_interpolation()

double gpmp::optim::Func::linear_interpolation ( double  x,
double  x0,
double  x1,
double  y0,
double  y1 
)

Interpolates a univariate function using linear interpolation.

Parameters
xThe point at which to interpolate
x0The left point of the interval
x1The right point of the interval
y0The function value at x0
y1The function value at x1
Returns
The interpolated function value at x

Definition at line 139 of file function.cpp.

143  {
144  return y0 + (y1 - y0) / (x1 - x0) * (x - x0);
145 }

◆ nelder_mead()

std::vector< double > gpmp::optim::Func::nelder_mead ( const std::function< double(const std::vector< double > &)> &  func,
std::vector< double >  initial_point,
double  tolerance,
size_t  max_iterations 
)

Finds the minimum of a multivariate function using the Nelder–Mead method.

Parameters
funcThe multivariate function to minimize
initial_pointThe initial guess for the minimum
toleranceThe tolerance for stopping criterion
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 519 of file function.cpp.

523  {
524  size_t n = initial_point.size();
525  std::vector<std::vector<double>> simplex(n + 1, initial_point);
526 
527  for (size_t i = 0; i < n; ++i) {
528  simplex[i][i] += 1.0;
529  }
530 
531  std::vector<double> values(n + 1);
532  for (size_t i = 0; i <= n; ++i) {
533  values[i] = func(simplex[i]);
534  }
535 
536  for (size_t iteration = 0; iteration < max_iterations; ++iteration) {
537  size_t highest_index =
538  std::distance(values.begin(),
539  std::max_element(values.begin(), values.end()));
540  size_t lowest_index =
541  std::distance(values.begin(),
542  std::min_element(values.begin(), values.end()));
543 
544  std::vector<double> centroid =
545  calculate_centroid(simplex, highest_index);
546 
547  // Reflect
548  std::vector<double> reflected_point =
549  reflect(simplex[highest_index], centroid, 1.0);
550  double reflected_value = func(reflected_point);
551 
552  if (reflected_value < values[lowest_index]) {
553  // Expand
554  std::vector<double> expanded_point =
555  reflect(simplex[highest_index], centroid, 2.0);
556  double expanded_value = func(expanded_point);
557 
558  if (expanded_value < reflected_value) {
559  simplex[highest_index] = expanded_point;
560  values[highest_index] = expanded_value;
561  } else {
562  simplex[highest_index] = reflected_point;
563  values[highest_index] = reflected_value;
564  }
565  } else if (reflected_value >= values[lowest_index] &&
566  reflected_value < values[highest_index]) {
567  simplex[highest_index] = reflected_point;
568  values[highest_index] = reflected_value;
569  } else {
570  // Contract
571  std::vector<double> contracted_point =
572  reflect(simplex[highest_index], centroid, 0.5);
573  double contracted_value = func(contracted_point);
574 
575  if (contracted_value < values[highest_index]) {
576  simplex[highest_index] = contracted_point;
577  values[highest_index] = contracted_value;
578  } else {
579  // Shrink
580  for (size_t i = 0; i <= n; ++i) {
581  if (i != lowest_index) {
582  for (size_t j = 0; j < n; ++j) {
583  simplex[i][j] = 0.5 * (simplex[i][j] +
584  simplex[lowest_index][j]);
585  }
586  values[i] = func(simplex[i]);
587  }
588  }
589  }
590  }
591 
592  // Check convergence
593  double range = calculate_range(values);
594  if (range < tolerance) {
595  return simplex[lowest_index];
596  }
597  }
598 
599  return simplex[std::distance(
600  values.begin(),
601  std::min_element(values.begin(), values.end()))];
602 }
std::vector< double > reflect(const std::vector< double > &point, const std::vector< double > &centroid, double reflection_coefficient)
Reflects a point with respect to a centroid.
Definition: function.cpp:628
double calculate_range(const std::vector< double > &values)
Calculates the range of values.
Definition: function.cpp:642
std::vector< double > calculate_centroid(const std::vector< std::vector< double >> &simplex, size_t exclude_index)
Calculates the centroid of a simplex excluding a specific point.
Definition: function.cpp:606

◆ newton_method()

std::vector< double > gpmp::optim::Func::newton_method ( const std::function< double(const std::vector< double > &)> &  func,
const std::function< double(const std::vector< double > &)> &  derivative,
double  initial_guess,
size_t  max_iterations 
)

Performs Newton's method for function optimization.

Parameters
funcThe univariate function to optimize
derivativeThe derivative of the function
initial_guessThe initial guess for the minimum
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 393 of file function.cpp.

397  {
398  double x = initial_guess;
399 
400  for (size_t iteration = 0; iteration < max_iterations; ++iteration) {
401  double fx = func({x});
402  double dfx = derivative({x});
403 
404  if ((fabs(dfx) - 0.0f) < std::numeric_limits<double>::epsilon()) {
405  throw std::runtime_error("Newton's method: Derivative is zero.");
406  }
407 
408  x = x - fx / dfx;
409  }
410 
411  return {x};
412 }

◆ random_search()

double gpmp::optim::Func::random_search ( const std::function< double(const std::vector< double > &)> &  func,
const std::vector< double > &  lower_bounds,
const std::vector< double > &  upper_bounds,
size_t  max_iterations 
)

Performs random search for function optimization.

Parameters
funcThe multivariate function to optimize
lower_boundsThe lower bounds of the search interval
upper_boundsThe upper bounds of the search interval
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 233 of file function.cpp.

237  {
238  if (lower_bounds.size() != upper_bounds.size()) {
239  throw std::invalid_argument(
240  "Lower and upper bounds must have the same dimension.");
241  }
242 
243  size_t dimension = lower_bounds.size();
244  std::vector<double> best_point(dimension);
245  double best_value = std::numeric_limits<double>::infinity();
246 
247  for (size_t iteration = 0; iteration < max_iterations; ++iteration) {
248  std::vector<double> random_point =
249  generate_random_point(lower_bounds, upper_bounds);
250  double value = func(random_point);
251 
252  if (value < best_value) {
253  best_value = value;
254  best_point = random_point;
255  }
256  }
257 
258  return best_value;
259 }
std::vector< double > generate_random_point(const std::vector< double > &lower_bounds, const std::vector< double > &upper_bounds) const
Generates a random point within specified bounds.
Definition: function.cpp:37

◆ reflect()

std::vector< double > gpmp::optim::Func::reflect ( const std::vector< double > &  point,
const std::vector< double > &  centroid,
double  reflection_coefficient 
)

Reflects a point with respect to a centroid.

Parameters
pointThe point to reflect
centroidThe centroid
reflection_coefficientThe reflection coefficient
Returns
The reflected point

Definition at line 628 of file function.cpp.

630  {
631  size_t n = point.size();
632  std::vector<double> reflected_point(n);
633 
634  for (size_t i = 0; i < n; ++i) {
635  reflected_point[i] =
636  centroid[i] + reflection_coefficient * (centroid[i] - point[i]);
637  }
638 
639  return reflected_point;
640 }

◆ regula_falsi()

std::vector< double > gpmp::optim::Func::regula_falsi ( const std::function< double(const std::vector< double > &)> &  func,
double  lower_bound,
double  upper_bound,
size_t  max_iterations 
)

Performs Regula Falsi (False Position) method for function optimization.

Parameters
funcThe univariate function to optimize
lower_boundThe lower bound of the search interval
upper_boundThe upper bound of the search interval
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 414 of file function.cpp.

418  {
419  if (func({lower_bound}) * func({upper_bound}) >= 0.0) {
420  throw std::invalid_argument("Invalid bounds for regula falsi method.");
421  }
422 
423  double a = lower_bound;
424  double b = upper_bound;
425 
426  for (size_t iteration = 0; iteration < max_iterations; ++iteration) {
427  double fa = func({a});
428  double fb = func({b});
429 
430  if (fa * fb >= 0.0) {
431  throw std::runtime_error("Regula falsi method: Function values at "
432  "the bounds have the same sign.");
433  }
434 
435  double c = (a * fb - b * fa) / (fb - fa);
436 
437  if (fabs(func({c}) - 0.0f) < std::numeric_limits<double>::epsilon()) {
438  return {c};
439  } else if (fa * func({c}) < 0.0) {
440  b = c;
441  } else {
442  a = c;
443  }
444  }
445 
446  return {(a + b) / 2.0};
447 }

◆ ternary_search()

double gpmp::optim::Func::ternary_search ( const std::function< double(const std::vector< double > &)> &  func,
const std::vector< double > &  lower_bounds,
const std::vector< double > &  upper_bounds,
size_t  max_iterations 
) const

Performs ternary search for function optimization.

Parameters
funcThe multivariate function to optimize
lower_boundsThe lower bounds of the search interval
upper_boundsThe upper bounds of the search interval
max_iterationsThe maximum number of iterations
Returns
The vector of arguments that minimizes the function

Definition at line 331 of file function.cpp.

335  {
336  double a = lower_bounds[0];
337  double b = upper_bounds[0];
338 
339  if (lower_bounds >= upper_bounds) {
340  throw std::invalid_argument("Invalid bounds for ternary search method");
341  }
342 
343  for (size_t iteration = 0; iteration < max_iterations; ++iteration) {
344  double m1 = calculate_midpoint(a, b, 1.0 / 3.0);
345  double m2 = calculate_midpoint(a, b, 2.0 / 3.0);
346 
347  double f_m1 = func({m1});
348  double f_m2 = func({m2});
349 
350  if (f_m1 < f_m2) {
351  b = m2;
352  } else {
353  a = m1;
354  }
355  }
356 
357  return calculate_midpoint(a, b, 0.5);
358 }

◆ vector_addition()

std::vector< double > gpmp::optim::Func::vector_addition ( const std::vector< double > &  a,
const std::vector< double > &  b 
) const

Performs vector addition.

Parameters
aThe first vector
bThe second vector
Returns
The result of vector addition

Definition at line 74 of file function.cpp.

75  {
76  if (a.size() != b.size()) {
77  throw std::invalid_argument(
78  "Vector dimensions do not match for addition.");
79  }
80 
81  std::vector<double> result;
82  for (size_t i = 0; i < a.size(); ++i) {
83  result.push_back(a[i] + b[i]);
84  }
85 
86  return result;
87 }

◆ vector_scalar_multiply()

std::vector< double > gpmp::optim::Func::vector_scalar_multiply ( double  scalar,
const std::vector< double > &  vec 
) const

Performs vector scalar multiplication.

Parameters
scalarThe scalar value
vecThe vector
Returns
The result of vector scalar multiplication

Definition at line 105 of file function.cpp.

107  {
108  std::vector<double> result;
109  for (double value : vec) {
110  result.push_back(scalar * value);
111  }
112 
113  return result;
114 }

◆ vector_subtraction()

std::vector< double > gpmp::optim::Func::vector_subtraction ( const std::vector< double > &  a,
const std::vector< double > &  b 
) const

Performs vector subtraction.

Parameters
aThe first vector
bThe second vector
Returns
The result of vector subtraction

Definition at line 90 of file function.cpp.

91  {
92  if (a.size() != b.size()) {
93  throw std::invalid_argument(
94  "Vector dimensions do not match for subtraction.");
95  }
96 
97  std::vector<double> result;
98  for (size_t i = 0; i < a.size(); ++i) {
99  result.push_back(a[i] - b[i]);
100  }
101 
102  return result;
103 }

The documentation for this class was generated from the following files: