Directory: | ./ |
---|---|
File: | src/core/solver-base.cpp |
Date: | 2025-01-16 08:47:40 |
Exec | Total | Coverage | |
---|---|---|---|
Lines: | 159 | 273 | 58.2% |
Branches: | 67 | 507 | 13.2% |
Line | Branch | Exec | Source |
---|---|---|---|
1 | /////////////////////////////////////////////////////////////////////////////// | ||
2 | // BSD 3-Clause License | ||
3 | // | ||
4 | // Copyright (C) 2019-2024, LAAS-CNRS, University of Edinburgh, | ||
5 | // Heriot-Watt University, University of Oxford | ||
6 | // Copyright note valid unless otherwise stated in individual files. | ||
7 | // All rights reserved. | ||
8 | /////////////////////////////////////////////////////////////////////////////// | ||
9 | |||
10 | #ifdef CROCODDYL_WITH_MULTITHREADING | ||
11 | #include <omp.h> | ||
12 | #endif // CROCODDYL_WITH_MULTITHREADING | ||
13 | |||
14 | #include "crocoddyl/core/solver-base.hpp" | ||
15 | #include "crocoddyl/core/utils/exception.hpp" | ||
16 | |||
17 | namespace crocoddyl { | ||
18 | |||
19 | 119 | SolverAbstract::SolverAbstract(boost::shared_ptr<ShootingProblem> problem) | |
20 | 119 | : problem_(problem), | |
21 | 119 | is_feasible_(false), | |
22 | 119 | was_feasible_(false), | |
23 | 119 | cost_(0.), | |
24 | 119 | merit_(0.), | |
25 | 119 | stop_(0.), | |
26 | 119 | dV_(0.), | |
27 | 119 | dPhi_(0.), | |
28 | 119 | dVexp_(0.), | |
29 | 119 | dPhiexp_(0.), | |
30 | 119 | dfeas_(0.), | |
31 | 119 | feas_(0.), | |
32 | 119 | ffeas_(0.), | |
33 | 119 | gfeas_(0.), | |
34 | 119 | hfeas_(0.), | |
35 | 119 | ffeas_try_(0.), | |
36 | 119 | gfeas_try_(0.), | |
37 | 119 | hfeas_try_(0.), | |
38 | 119 | preg_(0.), | |
39 | 119 | dreg_(0.), | |
40 | 119 | steplength_(1.), | |
41 | 119 | th_acceptstep_(0.1), | |
42 | 119 | th_stop_(1e-9), | |
43 | 119 | th_gaptol_(1e-16), | |
44 | 119 | feasnorm_(LInf), | |
45 | 119 | iter_(0), | |
46 |
1/2✓ Branch 6 taken 119 times.
✗ Branch 7 not taken.
|
119 | tmp_feas_(0.) { |
47 | // Allocate common data | ||
48 | 119 | const std::size_t ndx = problem_->get_ndx(); | |
49 | 119 | const std::size_t T = problem_->get_T(); | |
50 |
1/2✓ Branch 4 taken 119 times.
✗ Branch 5 not taken.
|
119 | const std::size_t ng_T = problem_->get_terminalModel()->get_ng_T(); |
51 |
1/2✓ Branch 1 taken 119 times.
✗ Branch 2 not taken.
|
119 | xs_.resize(T + 1); |
52 |
1/2✓ Branch 1 taken 119 times.
✗ Branch 2 not taken.
|
119 | us_.resize(T); |
53 |
1/2✓ Branch 1 taken 119 times.
✗ Branch 2 not taken.
|
119 | fs_.resize(T + 1); |
54 |
1/2✓ Branch 1 taken 119 times.
✗ Branch 2 not taken.
|
119 | g_adj_.resize(T + 1); |
55 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
56 | 119 | problem_->get_runningModels(); | |
57 |
2/2✓ Branch 0 taken 1148 times.
✓ Branch 1 taken 119 times.
|
1267 | for (std::size_t t = 0; t < T; ++t) { |
58 | 1148 | const boost::shared_ptr<ActionModelAbstract>& model = models[t]; | |
59 | 1148 | const std::size_t nu = model->get_nu(); | |
60 |
1/2✓ Branch 2 taken 1148 times.
✗ Branch 3 not taken.
|
1148 | const std::size_t ng = model->get_ng(); |
61 |
1/2✓ Branch 4 taken 1148 times.
✗ Branch 5 not taken.
|
1148 | xs_[t] = model->get_state()->zero(); |
62 |
2/4✓ Branch 1 taken 1148 times.
✗ Branch 2 not taken.
✓ Branch 5 taken 1148 times.
✗ Branch 6 not taken.
|
1148 | us_[t] = Eigen::VectorXd::Zero(nu); |
63 |
2/4✓ Branch 1 taken 1148 times.
✗ Branch 2 not taken.
✓ Branch 5 taken 1148 times.
✗ Branch 6 not taken.
|
1148 | fs_[t] = Eigen::VectorXd::Zero(ndx); |
64 |
2/4✓ Branch 1 taken 1148 times.
✗ Branch 2 not taken.
✓ Branch 5 taken 1148 times.
✗ Branch 6 not taken.
|
1148 | g_adj_[t] = Eigen::VectorXd::Zero(ng); |
65 | } | ||
66 |
1/2✓ Branch 6 taken 119 times.
✗ Branch 7 not taken.
|
119 | xs_.back() = problem_->get_terminalModel()->get_state()->zero(); |
67 |
2/4✓ Branch 1 taken 119 times.
✗ Branch 2 not taken.
✓ Branch 5 taken 119 times.
✗ Branch 6 not taken.
|
119 | fs_.back() = Eigen::VectorXd::Zero(ndx); |
68 |
2/4✓ Branch 1 taken 119 times.
✗ Branch 2 not taken.
✓ Branch 5 taken 119 times.
✗ Branch 6 not taken.
|
119 | g_adj_.back() = Eigen::VectorXd::Zero(ng_T); |
69 | 119 | } | |
70 | |||
71 | 266 | SolverAbstract::~SolverAbstract() {} | |
72 | |||
73 | ✗ | void SolverAbstract::resizeData() { | |
74 | ✗ | START_PROFILER("SolverAbstract::resizeData"); | |
75 | ✗ | const std::size_t T = problem_->get_T(); | |
76 | ✗ | const std::size_t ng_T = problem_->get_terminalModel()->get_ng_T(); | |
77 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
78 | ✗ | problem_->get_runningModels(); | |
79 | ✗ | for (std::size_t t = 0; t < T; ++t) { | |
80 | ✗ | const boost::shared_ptr<ActionModelAbstract>& model = models[t]; | |
81 | ✗ | const std::size_t nu = model->get_nu(); | |
82 | ✗ | const std::size_t ng = model->get_ng(); | |
83 | ✗ | us_[t].conservativeResize(nu); | |
84 | ✗ | g_adj_[t].conservativeResize(ng); | |
85 | } | ||
86 | |||
87 | ✗ | g_adj_.back().conservativeResize(ng_T); | |
88 | |||
89 | ✗ | STOP_PROFILER("SolverAbstract::resizeData"); | |
90 | } | ||
91 | |||
92 | 108 | double SolverAbstract::computeDynamicFeasibility() { | |
93 | 108 | tmp_feas_ = 0.; | |
94 | 108 | const std::size_t T = problem_->get_T(); | |
95 | 108 | const Eigen::VectorXd& x0 = problem_->get_x0(); | |
96 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
97 | 108 | problem_->get_runningModels(); | |
98 | const std::vector<boost::shared_ptr<ActionDataAbstract> >& datas = | ||
99 | 108 | problem_->get_runningDatas(); | |
100 | |||
101 |
3/6✓ Branch 7 taken 108 times.
✗ Branch 8 not taken.
✓ Branch 11 taken 108 times.
✗ Branch 12 not taken.
✓ Branch 14 taken 108 times.
✗ Branch 15 not taken.
|
108 | models[0]->get_state()->diff(xs_[0], x0, fs_[0]); |
102 | #ifdef CROCODDYL_WITH_MULTITHREADING | ||
103 | #pragma omp parallel for num_threads(problem_->get_nthreads()) | ||
104 | #endif | ||
105 |
2/2✓ Branch 0 taken 1152 times.
✓ Branch 1 taken 108 times.
|
1260 | for (std::size_t t = 0; t < T; ++t) { |
106 | 1152 | const boost::shared_ptr<ActionModelAbstract>& m = models[t]; | |
107 | 1152 | const boost::shared_ptr<ActionDataAbstract>& d = datas[t]; | |
108 |
3/6✓ Branch 7 taken 1152 times.
✗ Branch 8 not taken.
✓ Branch 11 taken 1152 times.
✗ Branch 12 not taken.
✓ Branch 14 taken 1152 times.
✗ Branch 15 not taken.
|
1152 | m->get_state()->diff(xs_[t + 1], d->xnext, fs_[t + 1]); |
109 | } | ||
110 |
1/3✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
|
108 | switch (feasnorm_) { |
111 | 108 | case LInf: | |
112 | 108 | tmp_feas_ = std::max(tmp_feas_, fs_[0].lpNorm<Eigen::Infinity>()); | |
113 |
2/2✓ Branch 0 taken 1152 times.
✓ Branch 1 taken 108 times.
|
1260 | for (std::size_t t = 0; t < T; ++t) { |
114 | 1152 | tmp_feas_ = std::max(tmp_feas_, fs_[t + 1].lpNorm<Eigen::Infinity>()); | |
115 | } | ||
116 | 108 | break; | |
117 | ✗ | case L1: | |
118 | ✗ | tmp_feas_ = fs_[0].lpNorm<1>(); | |
119 | ✗ | for (std::size_t t = 0; t < T; ++t) { | |
120 | ✗ | tmp_feas_ += fs_[t + 1].lpNorm<1>(); | |
121 | } | ||
122 | ✗ | break; | |
123 | } | ||
124 | 108 | return tmp_feas_; | |
125 | } | ||
126 | |||
127 | 108 | double SolverAbstract::computeInequalityFeasibility() { | |
128 | 108 | tmp_feas_ = 0.; | |
129 | 108 | const std::size_t T = problem_->get_T(); | |
130 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
131 | 108 | problem_->get_runningModels(); | |
132 | const std::vector<boost::shared_ptr<ActionDataAbstract> >& datas = | ||
133 | 108 | problem_->get_runningDatas(); | |
134 | |||
135 |
1/3✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
|
108 | switch (feasnorm_) { |
136 | 108 | case LInf: | |
137 |
2/2✓ Branch 0 taken 1152 times.
✓ Branch 1 taken 108 times.
|
1260 | for (std::size_t t = 0; t < T; ++t) { |
138 |
1/2✗ Branch 3 not taken.
✓ Branch 4 taken 1152 times.
|
1152 | if (models[t]->get_ng() > 0) { |
139 | ✗ | g_adj_[t] = datas[t] | |
140 | ✗ | ->g.cwiseMax(models[t]->get_g_lb()) | |
141 | ✗ | .cwiseMin(models[t]->get_g_ub()); | |
142 | ✗ | tmp_feas_ = std::max( | |
143 | ✗ | tmp_feas_, (datas[t]->g - g_adj_[t]).lpNorm<Eigen::Infinity>()); | |
144 | } | ||
145 | } | ||
146 |
1/2✗ Branch 4 not taken.
✓ Branch 5 taken 108 times.
|
108 | if (problem_->get_terminalModel()->get_ng_T() > 0) { |
147 | ✗ | g_adj_.back() = | |
148 | ✗ | problem_->get_terminalData() | |
149 | ✗ | ->g.cwiseMax(problem_->get_terminalModel()->get_g_lb()) | |
150 | ✗ | .cwiseMin(problem_->get_terminalModel()->get_g_ub()); | |
151 | ✗ | tmp_feas_ += (problem_->get_terminalData()->g - g_adj_.back()) | |
152 | ✗ | .lpNorm<Eigen::Infinity>(); | |
153 | } | ||
154 | 108 | break; | |
155 | ✗ | case L1: | |
156 | ✗ | for (std::size_t t = 0; t < T; ++t) { | |
157 | ✗ | if (models[t]->get_ng() > 0) { | |
158 | ✗ | g_adj_[t] = datas[t] | |
159 | ✗ | ->g.cwiseMax(models[t]->get_g_lb()) | |
160 | ✗ | .cwiseMin(models[t]->get_g_ub()); | |
161 | ✗ | tmp_feas_ = | |
162 | ✗ | std::max(tmp_feas_, (datas[t]->g - g_adj_[t]).lpNorm<1>()); | |
163 | } | ||
164 | } | ||
165 | ✗ | if (problem_->get_terminalModel()->get_ng_T() > 0) { | |
166 | ✗ | g_adj_.back() = | |
167 | ✗ | problem_->get_terminalData() | |
168 | ✗ | ->g.cwiseMax(problem_->get_terminalModel()->get_g_lb()) | |
169 | ✗ | .cwiseMin(problem_->get_terminalModel()->get_g_ub()); | |
170 | ✗ | tmp_feas_ += | |
171 | ✗ | (problem_->get_terminalData()->g - g_adj_.back()).lpNorm<1>(); | |
172 | } | ||
173 | ✗ | break; | |
174 | } | ||
175 | 108 | return tmp_feas_; | |
176 | } | ||
177 | |||
178 | 108 | double SolverAbstract::computeEqualityFeasibility() { | |
179 | 108 | tmp_feas_ = 0.; | |
180 | 108 | const std::size_t T = problem_->get_T(); | |
181 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
182 | 108 | problem_->get_runningModels(); | |
183 | const std::vector<boost::shared_ptr<ActionDataAbstract> >& datas = | ||
184 | 108 | problem_->get_runningDatas(); | |
185 |
1/3✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
|
108 | switch (feasnorm_) { |
186 | 108 | case LInf: | |
187 |
2/2✓ Branch 0 taken 1152 times.
✓ Branch 1 taken 108 times.
|
1260 | for (std::size_t t = 0; t < T; ++t) { |
188 |
1/2✗ Branch 3 not taken.
✓ Branch 4 taken 1152 times.
|
1152 | if (models[t]->get_nh() > 0) { |
189 | ✗ | tmp_feas_ = | |
190 | ✗ | std::max(tmp_feas_, datas[t]->h.lpNorm<Eigen::Infinity>()); | |
191 | } | ||
192 | } | ||
193 |
2/2✓ Branch 4 taken 8 times.
✓ Branch 5 taken 100 times.
|
108 | if (problem_->get_terminalModel()->get_nh_T() > 0) { |
194 | 8 | tmp_feas_ = | |
195 | 16 | std::max(tmp_feas_, | |
196 | 8 | problem_->get_terminalData()->h.lpNorm<Eigen::Infinity>()); | |
197 | } | ||
198 | 108 | break; | |
199 | ✗ | case L1: | |
200 | ✗ | for (std::size_t t = 0; t < T; ++t) { | |
201 | ✗ | if (models[t]->get_nh() > 0) { | |
202 | ✗ | tmp_feas_ += datas[t]->h.lpNorm<1>(); | |
203 | } | ||
204 | } | ||
205 | ✗ | if (problem_->get_terminalModel()->get_nh_T() > 0) { | |
206 | ✗ | tmp_feas_ += problem_->get_terminalData()->h.lpNorm<1>(); | |
207 | } | ||
208 | ✗ | break; | |
209 | } | ||
210 | 108 | return tmp_feas_; | |
211 | } | ||
212 | |||
213 | 313 | void SolverAbstract::setCandidate(const std::vector<Eigen::VectorXd>& xs_warm, | |
214 | const std::vector<Eigen::VectorXd>& us_warm, | ||
215 | bool is_feasible) { | ||
216 | 313 | const std::size_t T = problem_->get_T(); | |
217 | |||
218 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
219 | 313 | problem_->get_runningModels(); | |
220 |
2/2✓ Branch 1 taken 40 times.
✓ Branch 2 taken 273 times.
|
313 | if (xs_warm.size() == 0) { |
221 |
2/2✓ Branch 0 taken 360 times.
✓ Branch 1 taken 40 times.
|
400 | for (std::size_t t = 0; t < T; ++t) { |
222 | 360 | const boost::shared_ptr<ActionModelAbstract>& model = models[t]; | |
223 | 360 | xs_[t] = model->get_state()->zero(); | |
224 | } | ||
225 | 40 | xs_.back() = problem_->get_terminalModel()->get_state()->zero(); | |
226 | } else { | ||
227 |
1/2✗ Branch 1 not taken.
✓ Branch 2 taken 273 times.
|
273 | if (xs_warm.size() != T + 1) { |
228 | ✗ | throw_pretty("Warm start state vector has wrong dimension, got " | |
229 | << xs_warm.size() << " expecting " << (T + 1)); | ||
230 | } | ||
231 |
2/2✓ Branch 0 taken 2922 times.
✓ Branch 1 taken 273 times.
|
3195 | for (std::size_t t = 0; t < T; ++t) { |
232 | 2922 | const std::size_t nx = models[t]->get_state()->get_nx(); | |
233 |
1/2✗ Branch 2 not taken.
✓ Branch 3 taken 2922 times.
|
2922 | if (static_cast<std::size_t>(xs_warm[t].size()) != nx) { |
234 | ✗ | throw_pretty("Invalid argument: " | |
235 | << "xs_init[" + std::to_string(t) + | ||
236 | "] has wrong dimension (" | ||
237 | << xs_warm[t].size() | ||
238 | << " provided - it should be equal to " + | ||
239 | std::to_string(nx) + "). ActionModel: " | ||
240 | << *models[t]); | ||
241 | } | ||
242 | } | ||
243 | 273 | const std::size_t nx = problem_->get_terminalModel()->get_state()->get_nx(); | |
244 |
1/2✗ Branch 2 not taken.
✓ Branch 3 taken 273 times.
|
273 | if (static_cast<std::size_t>(xs_warm[T].size()) != nx) { |
245 | ✗ | throw_pretty("Invalid argument: " | |
246 | << "xs_init[" + std::to_string(T) + | ||
247 | "] (terminal state) has wrong dimension (" | ||
248 | << xs_warm[T].size() | ||
249 | << " provided - it should be equal to " + | ||
250 | std::to_string(nx) + "). ActionModel: " | ||
251 | << *problem_->get_terminalModel()); | ||
252 | } | ||
253 | 273 | std::copy(xs_warm.begin(), xs_warm.end(), xs_.begin()); | |
254 | } | ||
255 | |||
256 |
2/2✓ Branch 1 taken 40 times.
✓ Branch 2 taken 273 times.
|
313 | if (us_warm.size() == 0) { |
257 |
2/2✓ Branch 0 taken 360 times.
✓ Branch 1 taken 40 times.
|
400 | for (std::size_t t = 0; t < T; ++t) { |
258 | 360 | const boost::shared_ptr<ActionModelAbstract>& model = models[t]; | |
259 | 360 | const std::size_t nu = model->get_nu(); | |
260 |
1/2✓ Branch 3 taken 360 times.
✗ Branch 4 not taken.
|
360 | us_[t] = Eigen::VectorXd::Zero(nu); |
261 | } | ||
262 | } else { | ||
263 |
1/2✗ Branch 1 not taken.
✓ Branch 2 taken 273 times.
|
273 | if (us_warm.size() != T) { |
264 | ✗ | throw_pretty("Warm start control has wrong dimension, got " | |
265 | << us_warm.size() << " expecting " << T); | ||
266 | } | ||
267 |
2/2✓ Branch 0 taken 2922 times.
✓ Branch 1 taken 273 times.
|
3195 | for (std::size_t t = 0; t < T; ++t) { |
268 | 2922 | const boost::shared_ptr<ActionModelAbstract>& model = models[t]; | |
269 | 2922 | const std::size_t nu = model->get_nu(); | |
270 |
1/2✗ Branch 2 not taken.
✓ Branch 3 taken 2922 times.
|
2922 | if (static_cast<std::size_t>(us_warm[t].size()) != nu) { |
271 | ✗ | throw_pretty("Invalid argument: " | |
272 | << "us_init[" + std::to_string(t) + | ||
273 | "] has wrong dimension (" | ||
274 | << us_warm[t].size() | ||
275 | << " provided - it should be equal to " + | ||
276 | std::to_string(nu) + "). ActionModel: " | ||
277 | << *model); | ||
278 | } | ||
279 | } | ||
280 | 273 | std::copy(us_warm.begin(), us_warm.end(), us_.begin()); | |
281 | } | ||
282 | 313 | is_feasible_ = is_feasible; | |
283 | 313 | } | |
284 | |||
285 | 50 | void SolverAbstract::setCallbacks( | |
286 | const std::vector<boost::shared_ptr<CallbackAbstract> >& callbacks) { | ||
287 | 50 | callbacks_ = callbacks; | |
288 | 50 | } | |
289 | |||
290 | const std::vector<boost::shared_ptr<CallbackAbstract> >& | ||
291 | ✗ | SolverAbstract::getCallbacks() const { | |
292 | ✗ | return callbacks_; | |
293 | } | ||
294 | |||
295 | 1769 | const boost::shared_ptr<ShootingProblem>& SolverAbstract::get_problem() const { | |
296 | 1769 | return problem_; | |
297 | } | ||
298 | |||
299 | 607 | const std::vector<Eigen::VectorXd>& SolverAbstract::get_xs() const { | |
300 | 607 | return xs_; | |
301 | } | ||
302 | |||
303 | 532 | const std::vector<Eigen::VectorXd>& SolverAbstract::get_us() const { | |
304 | 532 | return us_; | |
305 | } | ||
306 | |||
307 | ✗ | const std::vector<Eigen::VectorXd>& SolverAbstract::get_fs() const { | |
308 | ✗ | return fs_; | |
309 | } | ||
310 | |||
311 | ✗ | bool SolverAbstract::get_is_feasible() const { return is_feasible_; } | |
312 | |||
313 | 104 | double SolverAbstract::get_cost() const { return cost_; } | |
314 | |||
315 | 104 | double SolverAbstract::get_merit() const { return merit_; } | |
316 | |||
317 | 104 | double SolverAbstract::get_stop() const { return stop_; } | |
318 | |||
319 | 104 | const Eigen::Vector2d& SolverAbstract::get_d() const { return d_; } | |
320 | |||
321 | 104 | double SolverAbstract::get_dV() const { return dV_; } | |
322 | |||
323 | 104 | double SolverAbstract::get_dPhi() const { return dPhi_; } | |
324 | |||
325 | 104 | double SolverAbstract::get_dVexp() const { return dVexp_; } | |
326 | |||
327 | 104 | double SolverAbstract::get_dPhiexp() const { return dPhiexp_; } | |
328 | |||
329 | ✗ | double SolverAbstract::get_dfeas() const { return dfeas_; } | |
330 | |||
331 | ✗ | double SolverAbstract::get_feas() const { return feas_; } | |
332 | |||
333 | 104 | double SolverAbstract::get_ffeas() const { return ffeas_; } | |
334 | |||
335 | 104 | double SolverAbstract::get_gfeas() const { return gfeas_; } | |
336 | |||
337 | 104 | double SolverAbstract::get_hfeas() const { return hfeas_; } | |
338 | |||
339 | ✗ | double SolverAbstract::get_ffeas_try() const { return ffeas_try_; } | |
340 | |||
341 | ✗ | double SolverAbstract::get_gfeas_try() const { return gfeas_try_; } | |
342 | |||
343 | ✗ | double SolverAbstract::get_hfeas_try() const { return hfeas_try_; } | |
344 | |||
345 | 3128 | double SolverAbstract::get_preg() const { return preg_; } | |
346 | |||
347 | 104 | double SolverAbstract::get_dreg() const { return dreg_; } | |
348 | |||
349 | ✗ | DEPRECATED( | |
350 | "Use get_preg for gettting the primal-dual regularization", | ||
351 | double SolverAbstract::get_xreg() const { return preg_; }) | ||
352 | |||
353 | ✗ | DEPRECATED( | |
354 | "Use get_preg for gettting the primal-dual regularization", | ||
355 | double SolverAbstract::get_ureg() const { return preg_; }) | ||
356 | |||
357 | 104 | double SolverAbstract::get_steplength() const { return steplength_; } | |
358 | |||
359 | 44 | double SolverAbstract::get_th_acceptstep() const { return th_acceptstep_; } | |
360 | |||
361 | 44 | double SolverAbstract::get_th_stop() const { return th_stop_; } | |
362 | |||
363 | ✗ | double SolverAbstract::get_th_gaptol() const { return th_gaptol_; } | |
364 | |||
365 | ✗ | FeasibilityNorm SolverAbstract::get_feasnorm() const { return feasnorm_; } | |
366 | |||
367 | 208 | std::size_t SolverAbstract::get_iter() const { return iter_; } | |
368 | |||
369 | ✗ | void SolverAbstract::set_xs(const std::vector<Eigen::VectorXd>& xs) { | |
370 | ✗ | const std::size_t T = problem_->get_T(); | |
371 | ✗ | if (xs.size() != T + 1) { | |
372 | ✗ | throw_pretty("Invalid argument: " << "xs list has to be of length " + | |
373 | std::to_string(T + 1)); | ||
374 | } | ||
375 | |||
376 | ✗ | const std::size_t nx = problem_->get_nx(); | |
377 | ✗ | for (std::size_t t = 0; t < T; ++t) { | |
378 | ✗ | if (static_cast<std::size_t>(xs[t].size()) != nx) { | |
379 | ✗ | throw_pretty("Invalid argument: " | |
380 | << "xs[" + std::to_string(t) + "] has wrong dimension (" | ||
381 | << xs[t].size() | ||
382 | << " provided - it should be " + std::to_string(nx) + ")") | ||
383 | } | ||
384 | } | ||
385 | ✗ | if (static_cast<std::size_t>(xs[T].size()) != nx) { | |
386 | ✗ | throw_pretty("Invalid argument: " | |
387 | << "xs[" + std::to_string(T) + | ||
388 | "] (terminal state) has wrong dimension (" | ||
389 | << xs[T].size() | ||
390 | << " provided - it should be " + std::to_string(nx) + ")") | ||
391 | } | ||
392 | ✗ | xs_ = xs; | |
393 | } | ||
394 | |||
395 | ✗ | void SolverAbstract::set_us(const std::vector<Eigen::VectorXd>& us) { | |
396 | ✗ | const std::size_t T = problem_->get_T(); | |
397 | ✗ | if (us.size() != T) { | |
398 | ✗ | throw_pretty("Invalid argument: " << "us list has to be of length " + | |
399 | std::to_string(T)); | ||
400 | } | ||
401 | |||
402 | const std::vector<boost::shared_ptr<ActionModelAbstract> >& models = | ||
403 | ✗ | problem_->get_runningModels(); | |
404 | ✗ | for (std::size_t t = 0; t < T; ++t) { | |
405 | ✗ | const boost::shared_ptr<ActionModelAbstract>& model = models[t]; | |
406 | ✗ | const std::size_t nu = model->get_nu(); | |
407 | ✗ | if (static_cast<std::size_t>(us[t].size()) != nu) { | |
408 | ✗ | throw_pretty("Invalid argument: " | |
409 | << "us[" + std::to_string(t) + "] has wrong dimension (" | ||
410 | << us[t].size() | ||
411 | << " provided - it should be " + std::to_string(nu) + ")") | ||
412 | } | ||
413 | } | ||
414 | ✗ | us_ = us; | |
415 | } | ||
416 | |||
417 | 148 | void SolverAbstract::set_preg(const double preg) { | |
418 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 148 times.
|
148 | if (preg < 0.) { |
419 | ✗ | throw_pretty("Invalid argument: " << "preg value has to be positive."); | |
420 | } | ||
421 | 148 | preg_ = preg; | |
422 | 148 | } | |
423 | |||
424 | 92 | void SolverAbstract::set_dreg(const double dreg) { | |
425 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 92 times.
|
92 | if (dreg < 0.) { |
426 | ✗ | throw_pretty("Invalid argument: " << "dreg value has to be positive."); | |
427 | } | ||
428 | 92 | dreg_ = dreg; | |
429 | 92 | } | |
430 | |||
431 | ✗ | DEPRECATED( | |
432 | "Use set_preg for gettting the primal-variable regularization", | ||
433 | void SolverAbstract::set_xreg(const double xreg) { | ||
434 | if (xreg < 0.) { | ||
435 | throw_pretty("Invalid argument: " << "xreg value has to be positive."); | ||
436 | } | ||
437 | xreg_ = xreg; | ||
438 | preg_ = xreg; | ||
439 | }) | ||
440 | |||
441 | ✗ | DEPRECATED( | |
442 | "Use set_preg for gettting the primal-variable regularization", | ||
443 | void SolverAbstract::set_ureg(const double ureg) { | ||
444 | if (ureg < 0.) { | ||
445 | throw_pretty("Invalid argument: " << "ureg value has to be positive."); | ||
446 | } | ||
447 | ureg_ = ureg; | ||
448 | preg_ = ureg; | ||
449 | }) | ||
450 | |||
451 | ✗ | void SolverAbstract::set_th_acceptstep(const double th_acceptstep) { | |
452 | ✗ | if (0. >= th_acceptstep || th_acceptstep > 1) { | |
453 | ✗ | throw_pretty( | |
454 | "Invalid argument: " << "th_acceptstep value should between 0 and 1."); | ||
455 | } | ||
456 | ✗ | th_acceptstep_ = th_acceptstep; | |
457 | } | ||
458 | |||
459 | ✗ | void SolverAbstract::set_th_stop(const double th_stop) { | |
460 | ✗ | if (th_stop <= 0.) { | |
461 | ✗ | throw_pretty("Invalid argument: " << "th_stop value has to higher than 0."); | |
462 | } | ||
463 | ✗ | th_stop_ = th_stop; | |
464 | } | ||
465 | |||
466 | ✗ | void SolverAbstract::set_th_gaptol(const double th_gaptol) { | |
467 | ✗ | if (0. > th_gaptol) { | |
468 | ✗ | throw_pretty("Invalid argument: " << "th_gaptol value has to be positive."); | |
469 | } | ||
470 | ✗ | th_gaptol_ = th_gaptol; | |
471 | } | ||
472 | |||
473 | ✗ | void SolverAbstract::set_feasnorm(const FeasibilityNorm feasnorm) { | |
474 | ✗ | feasnorm_ = feasnorm; | |
475 | } | ||
476 | |||
477 | 4728 | bool raiseIfNaN(const double value) { | |
478 |
4/8✓ Branch 1 taken 4728 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 4728 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 4728 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 4728 times.
|
4728 | if (std::isnan(value) || std::isinf(value) || value >= 1e30) { |
479 | ✗ | return true; | |
480 | } else { | ||
481 | 4728 | return false; | |
482 | } | ||
483 | } | ||
484 | |||
485 | } // namespace crocoddyl | ||
486 |