This repository was archived by the owner on Apr 24, 2025. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathGradientDescent.cpp
More file actions
77 lines (58 loc) · 3.49 KB
/
Copy pathGradientDescent.cpp
File metadata and controls
77 lines (58 loc) · 3.49 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
// This will be the main function of my program for GRADIANT DESCENT
// Here I introduce all the library I need for the execution
#include <iostream>
#include "Point.hpp"
#include "lib/GetPot"
#include "muparserX_fun.hpp"
#include "GradientDescentSolver.hpp"
//@note nice, but if yoou have a main that accepts options it is nice to have the option -h that prints a short help
int main(int argc, char **argv){
/*Here we find the section related to the "READING FROM data.txt"*/
GetPot command_line(argc, argv);
const std::string filename = command_line.follow("data_dir/data.txt", 2, "-f", "--file");
GetPot datafile(filename.c_str());
const std::string section = "GradientDescent/";
/*Here I couldn't find how to read directly from the data.txt a vector
of doubles, so I found online that this is a possible solution.
Obviously it is not highly performant, but it suits the purpose.*/
std::vector<std::string> dfunsString;
std::string x0 =datafile((section + "start").data()," ");
std::istringstream stm(x0) ;
std::vector<double> start_point;
double n ;
while( stm >> n ) start_point.emplace_back(n) ;
const unsigned int max_it = datafile((section + "max_it").data(),2000);
const double eps_step = datafile((section + "tol_step").data(),1e-6);
const double eps_res = datafile((section + "tol_res").data(),1e-6);
const double learning_rate = datafile((section + "learning_rate").data(),0.1);
const std::string rate_rule = datafile((section + "rate_rule").data(),"exponential decay");
const size_t dim = datafile((section + "dim").data(),2);
const double mu = datafile((section + "mu").data(),0.2);
const double sigma = datafile((section + "sigma").data(),0.25);
const double h = datafile((section + "h").data(),1e-6);
const bool exact = datafile((section + "exact").data(),false);
const std::string FDM_type = datafile((section + "FDM_type").data(),"CD");
Point start(dim,start_point);
// funString contains the string identifing our function to minimize
std::string funString = datafile((section + "fun").data()," ");
/*In this section we create the "real" function. In fact the class MuparserXFun uses the library muparserx to parse the variables
of the function directly from a std::string and can evaluate the value of a MuparserXFun in a Point class member.*/
MuparserXFun fun(funString, dim);
/*Since when we work with functions with more than 1 variable we come into GRADIENTS.
I define a vector which will contain all the string of the gradients w.r.t every variable (x0,x1,x2,...)*/
std::vector<MuparserXFun> dfuns;
if(exact){
/*Just recall we are in dim >= 2 so the gradients will be a vector of MuparserXFun*/
for(size_t i = 0; i < dim; ++i){
dfunsString.emplace_back(datafile((section + "dfun" + std::to_string(i)).data(), " "));
MuparserXFun dfun(dfunsString[i], dim);
dfuns.emplace_back(dfun);
}
}
/*Here I instantiate the Gradient Descent Solver passing it all the requirments.
In the end we print the minimum of our function if found, 0. otherwise*/
GradientDescentSolver solver(fun,dfuns,max_it,eps_step,eps_res,learning_rate,rate_rule,mu,sigma,exact,h,FDM_type);
double result = solver.Solver(start);
std::cout << "Value of the function in the last iteration: " << result << std::endl;
return 0;
}