GCC Code Coverage Report | |||||||||||||||||||||
|
|||||||||||||||||||||
Line | Branch | Exec | Source |
1 |
/////////////////////////////////////////////////////////////////////////////// |
||
2 |
// BSD 3-Clause License |
||
3 |
// |
||
4 |
// Copyright (C) 2019-2022, LAAS-CNRS, University of Edinburgh, |
||
5 |
// Heriot-Watt University |
||
6 |
// Copyright note valid unless otherwise stated in individual files. |
||
7 |
// All rights reserved. |
||
8 |
/////////////////////////////////////////////////////////////////////////////// |
||
9 |
|||
10 |
#include "crocoddyl/core/utils/exception.hpp" |
||
11 |
|||
12 |
namespace crocoddyl { |
||
13 |
|||
14 |
template <typename Scalar> |
||
15 |
72 |
ActionModelLQRTpl<Scalar>::ActionModelLQRTpl(const std::size_t nx, |
|
16 |
const std::size_t nu, |
||
17 |
const bool drift_free) |
||
18 |
: Base(boost::make_shared<StateVector>(nx), nu, 0), |
||
19 |
✓✗✓✗ ✓✗✓✗ ✓✗✓✗ ✓✗✓✗ ✓✗✓✗ |
72 |
drift_free_(drift_free) { |
20 |
// TODO(cmastalli): substitute by random (vectors) and random-orthogonal |
||
21 |
// (matrices) |
||
22 |
✓✗✓✗ |
72 |
Fx_ = MatrixXs::Identity(nx, nx); |
23 |
✓✗✓✗ |
72 |
Fu_ = MatrixXs::Identity(nx, nu); |
24 |
✓✗✓✗ |
72 |
f0_ = VectorXs::Ones(nx); |
25 |
✓✗✓✗ |
72 |
Lxx_ = MatrixXs::Identity(nx, nx); |
26 |
✓✗✓✗ |
72 |
Lxu_ = MatrixXs::Identity(nx, nu); |
27 |
✓✗✓✗ |
72 |
Luu_ = MatrixXs::Identity(nu, nu); |
28 |
✓✗✓✗ |
72 |
lx_ = VectorXs::Ones(nx); |
29 |
✓✗✓✗ |
72 |
lu_ = VectorXs::Ones(nu); |
30 |
72 |
} |
|
31 |
|||
32 |
template <typename Scalar> |
||
33 |
148 |
ActionModelLQRTpl<Scalar>::~ActionModelLQRTpl() {} |
|
34 |
|||
35 |
template <typename Scalar> |
||
36 |
1368 |
void ActionModelLQRTpl<Scalar>::calc( |
|
37 |
const boost::shared_ptr<ActionDataAbstract>& data, |
||
38 |
const Eigen::Ref<const VectorXs>& x, const Eigen::Ref<const VectorXs>& u) { |
||
39 |
✗✓ | 1368 |
if (static_cast<std::size_t>(x.size()) != state_->get_nx()) { |
40 |
throw_pretty("Invalid argument: " |
||
41 |
<< "x has wrong dimension (it should be " + |
||
42 |
std::to_string(state_->get_nx()) + ")"); |
||
43 |
} |
||
44 |
✗✓ | 1368 |
if (static_cast<std::size_t>(u.size()) != nu_) { |
45 |
throw_pretty("Invalid argument: " |
||
46 |
<< "u has wrong dimension (it should be " + |
||
47 |
std::to_string(nu_) + ")"); |
||
48 |
} |
||
49 |
1368 |
Data* d = static_cast<Data*>(data.get()); |
|
50 |
|||
51 |
✓✓ | 1368 |
if (drift_free_) { |
52 |
✓✗✓✗ |
655 |
data->xnext.noalias() = Fx_ * x; |
53 |
✓✗✓✗ |
655 |
data->xnext.noalias() += Fu_ * u; |
54 |
} else { |
||
55 |
✓✗✓✗ |
713 |
data->xnext.noalias() = Fx_ * x; |
56 |
✓✗✓✗ |
713 |
data->xnext.noalias() += Fu_ * u; |
57 |
713 |
data->xnext += f0_; |
|
58 |
} |
||
59 |
|||
60 |
// cost = 0.5 * x^T*Lxx*x + 0.5 * u^T*Luu*u + x^T*Lxu*u + lx^T*x + lu^T*u |
||
61 |
✓✗✓✗ |
1368 |
d->Lxx_x_tmp.noalias() = Lxx_ * x; |
62 |
1368 |
data->cost = Scalar(0.5) * x.dot(d->Lxx_x_tmp); |
|
63 |
✓✗✓✗ |
1368 |
d->Luu_u_tmp.noalias() = Luu_ * u; |
64 |
1368 |
data->cost += Scalar(0.5) * u.dot(d->Luu_u_tmp); |
|
65 |
✓✗✓✗ |
1368 |
d->Lxx_x_tmp.noalias() = Lxu_ * u; |
66 |
1368 |
data->cost += x.dot(d->Lxx_x_tmp); |
|
67 |
✓✗✓✗ |
1368 |
data->cost += lx_.transpose() * x; |
68 |
✓✗✓✗ |
1368 |
data->cost += lu_.transpose() * u; |
69 |
1368 |
} |
|
70 |
|||
71 |
template <typename Scalar> |
||
72 |
116 |
void ActionModelLQRTpl<Scalar>::calc( |
|
73 |
const boost::shared_ptr<ActionDataAbstract>& data, |
||
74 |
const Eigen::Ref<const VectorXs>& x) { |
||
75 |
✗✓ | 116 |
if (static_cast<std::size_t>(x.size()) != state_->get_nx()) { |
76 |
throw_pretty("Invalid argument: " |
||
77 |
<< "x has wrong dimension (it should be " + |
||
78 |
std::to_string(state_->get_nx()) + ")"); |
||
79 |
} |
||
80 |
116 |
Data* d = static_cast<Data*>(data.get()); |
|
81 |
|||
82 |
116 |
d->xnext = x; |
|
83 |
// cost = 0.5 * x^T*Lxx*x + lx^T*x |
||
84 |
✓✗✓✗ |
116 |
d->Lxx_x_tmp.noalias() = Lxx_ * x; |
85 |
116 |
data->cost = Scalar(0.5) * x.dot(d->Lxx_x_tmp); |
|
86 |
116 |
data->cost += lx_.dot(x); |
|
87 |
116 |
} |
|
88 |
|||
89 |
template <typename Scalar> |
||
90 |
863 |
void ActionModelLQRTpl<Scalar>::calcDiff( |
|
91 |
const boost::shared_ptr<ActionDataAbstract>& data, |
||
92 |
const Eigen::Ref<const VectorXs>& x, const Eigen::Ref<const VectorXs>& u) { |
||
93 |
✗✓ | 863 |
if (static_cast<std::size_t>(x.size()) != state_->get_nx()) { |
94 |
throw_pretty("Invalid argument: " |
||
95 |
<< "x has wrong dimension (it should be " + |
||
96 |
std::to_string(state_->get_nx()) + ")"); |
||
97 |
} |
||
98 |
✗✓ | 863 |
if (static_cast<std::size_t>(u.size()) != nu_) { |
99 |
throw_pretty("Invalid argument: " |
||
100 |
<< "u has wrong dimension (it should be " + |
||
101 |
std::to_string(nu_) + ")"); |
||
102 |
} |
||
103 |
|||
104 |
863 |
data->Lx = lx_; |
|
105 |
✓✗✓✗ |
863 |
data->Lx.noalias() += Lxx_ * x; |
106 |
✓✗✓✗ |
863 |
data->Lx.noalias() += Lxu_ * u; |
107 |
863 |
data->Lu = lu_; |
|
108 |
✓✗✓✗ ✓✗ |
863 |
data->Lu.noalias() += Lxu_.transpose() * x; |
109 |
✓✗✓✗ |
863 |
data->Lu.noalias() += Luu_ * u; |
110 |
863 |
data->Fx = Fx_; |
|
111 |
863 |
data->Fu = Fu_; |
|
112 |
863 |
data->Lxx = Lxx_; |
|
113 |
863 |
data->Lxu = Lxu_; |
|
114 |
863 |
data->Luu = Luu_; |
|
115 |
863 |
} |
|
116 |
|||
117 |
template <typename Scalar> |
||
118 |
55 |
void ActionModelLQRTpl<Scalar>::calcDiff( |
|
119 |
const boost::shared_ptr<ActionDataAbstract>& data, |
||
120 |
const Eigen::Ref<const VectorXs>& x) { |
||
121 |
✗✓ | 55 |
if (static_cast<std::size_t>(x.size()) != state_->get_nx()) { |
122 |
throw_pretty("Invalid argument: " |
||
123 |
<< "x has wrong dimension (it should be " + |
||
124 |
std::to_string(state_->get_nx()) + ")"); |
||
125 |
} |
||
126 |
|||
127 |
55 |
data->Lx = lx_; |
|
128 |
✓✗✓✗ |
55 |
data->Lx.noalias() += Lxx_ * x; |
129 |
55 |
data->Lxx = Lxx_; |
|
130 |
55 |
} |
|
131 |
|||
132 |
template <typename Scalar> |
||
133 |
boost::shared_ptr<ActionDataAbstractTpl<Scalar>> |
||
134 |
823 |
ActionModelLQRTpl<Scalar>::createData() { |
|
135 |
✓✗ | 823 |
return boost::allocate_shared<Data>(Eigen::aligned_allocator<Data>(), this); |
136 |
} |
||
137 |
|||
138 |
template <typename Scalar> |
||
139 |
128 |
bool ActionModelLQRTpl<Scalar>::checkData( |
|
140 |
const boost::shared_ptr<ActionDataAbstract>& data) { |
||
141 |
256 |
boost::shared_ptr<Data> d = boost::dynamic_pointer_cast<Data>(data); |
|
142 |
✓✗ | 128 |
if (d != NULL) { |
143 |
128 |
return true; |
|
144 |
} else { |
||
145 |
return false; |
||
146 |
} |
||
147 |
} |
||
148 |
|||
149 |
template <typename Scalar> |
||
150 |
44 |
void ActionModelLQRTpl<Scalar>::print(std::ostream& os) const { |
|
151 |
44 |
os << "ActionModelLQR {nx=" << state_->get_nx() << ", nu=" << nu_ |
|
152 |
44 |
<< ", drift_free=" << drift_free_ << "}"; |
|
153 |
44 |
} |
|
154 |
|||
155 |
template <typename Scalar> |
||
156 |
const typename MathBaseTpl<Scalar>::MatrixXs& |
||
157 |
823 |
ActionModelLQRTpl<Scalar>::get_Fx() const { |
|
158 |
823 |
return Fx_; |
|
159 |
} |
||
160 |
|||
161 |
template <typename Scalar> |
||
162 |
const typename MathBaseTpl<Scalar>::MatrixXs& |
||
163 |
823 |
ActionModelLQRTpl<Scalar>::get_Fu() const { |
|
164 |
823 |
return Fu_; |
|
165 |
} |
||
166 |
|||
167 |
template <typename Scalar> |
||
168 |
const typename MathBaseTpl<Scalar>::VectorXs& |
||
169 |
ActionModelLQRTpl<Scalar>::get_f0() const { |
||
170 |
return f0_; |
||
171 |
} |
||
172 |
|||
173 |
template <typename Scalar> |
||
174 |
const typename MathBaseTpl<Scalar>::VectorXs& |
||
175 |
ActionModelLQRTpl<Scalar>::get_lx() const { |
||
176 |
return lx_; |
||
177 |
} |
||
178 |
|||
179 |
template <typename Scalar> |
||
180 |
const typename MathBaseTpl<Scalar>::VectorXs& |
||
181 |
ActionModelLQRTpl<Scalar>::get_lu() const { |
||
182 |
return lu_; |
||
183 |
} |
||
184 |
|||
185 |
template <typename Scalar> |
||
186 |
const typename MathBaseTpl<Scalar>::MatrixXs& |
||
187 |
823 |
ActionModelLQRTpl<Scalar>::get_Lxx() const { |
|
188 |
823 |
return Lxx_; |
|
189 |
} |
||
190 |
|||
191 |
template <typename Scalar> |
||
192 |
const typename MathBaseTpl<Scalar>::MatrixXs& |
||
193 |
823 |
ActionModelLQRTpl<Scalar>::get_Lxu() const { |
|
194 |
823 |
return Lxu_; |
|
195 |
} |
||
196 |
|||
197 |
template <typename Scalar> |
||
198 |
const typename MathBaseTpl<Scalar>::MatrixXs& |
||
199 |
823 |
ActionModelLQRTpl<Scalar>::get_Luu() const { |
|
200 |
823 |
return Luu_; |
|
201 |
} |
||
202 |
|||
203 |
template <typename Scalar> |
||
204 |
void ActionModelLQRTpl<Scalar>::set_Fx(const MatrixXs& Fx) { |
||
205 |
if (static_cast<std::size_t>(Fx.rows()) != state_->get_nx() || |
||
206 |
static_cast<std::size_t>(Fx.cols()) != state_->get_nx()) { |
||
207 |
throw_pretty("Invalid argument: " |
||
208 |
<< "Fx has wrong dimension (it should be " + |
||
209 |
std::to_string(state_->get_nx()) + "," + |
||
210 |
std::to_string(state_->get_nx()) + ")"); |
||
211 |
} |
||
212 |
Fx_ = Fx; |
||
213 |
} |
||
214 |
|||
215 |
template <typename Scalar> |
||
216 |
void ActionModelLQRTpl<Scalar>::set_Fu(const MatrixXs& Fu) { |
||
217 |
if (static_cast<std::size_t>(Fu.rows()) != state_->get_nx() || |
||
218 |
static_cast<std::size_t>(Fu.cols()) != nu_) { |
||
219 |
throw_pretty("Invalid argument: " |
||
220 |
<< "Fu has wrong dimension (it should be " + |
||
221 |
std::to_string(state_->get_nx()) + "," + |
||
222 |
std::to_string(nu_) + ")"); |
||
223 |
} |
||
224 |
Fu_ = Fu; |
||
225 |
} |
||
226 |
|||
227 |
template <typename Scalar> |
||
228 |
void ActionModelLQRTpl<Scalar>::set_f0(const VectorXs& f0) { |
||
229 |
if (static_cast<std::size_t>(f0.size()) != state_->get_nx()) { |
||
230 |
throw_pretty("Invalid argument: " |
||
231 |
<< "f0 has wrong dimension (it should be " + |
||
232 |
std::to_string(state_->get_nx()) + ")"); |
||
233 |
} |
||
234 |
f0_ = f0; |
||
235 |
} |
||
236 |
|||
237 |
template <typename Scalar> |
||
238 |
void ActionModelLQRTpl<Scalar>::set_lx(const VectorXs& lx) { |
||
239 |
if (static_cast<std::size_t>(lx.size()) != state_->get_nx()) { |
||
240 |
throw_pretty("Invalid argument: " |
||
241 |
<< "lx has wrong dimension (it should be " + |
||
242 |
std::to_string(state_->get_nx()) + ")"); |
||
243 |
} |
||
244 |
lx_ = lx; |
||
245 |
} |
||
246 |
|||
247 |
template <typename Scalar> |
||
248 |
void ActionModelLQRTpl<Scalar>::set_lu(const VectorXs& lu) { |
||
249 |
if (static_cast<std::size_t>(lu.size()) != nu_) { |
||
250 |
throw_pretty("Invalid argument: " |
||
251 |
<< "lu has wrong dimension (it should be " + |
||
252 |
std::to_string(nu_) + ")"); |
||
253 |
} |
||
254 |
lu_ = lu; |
||
255 |
} |
||
256 |
|||
257 |
template <typename Scalar> |
||
258 |
void ActionModelLQRTpl<Scalar>::set_Lxx(const MatrixXs& Lxx) { |
||
259 |
if (static_cast<std::size_t>(Lxx.rows()) != state_->get_nx() || |
||
260 |
static_cast<std::size_t>(Lxx.cols()) != state_->get_nx()) { |
||
261 |
throw_pretty("Invalid argument: " |
||
262 |
<< "Lxx has wrong dimension (it should be " + |
||
263 |
std::to_string(state_->get_nx()) + "," + |
||
264 |
std::to_string(state_->get_nx()) + ")"); |
||
265 |
} |
||
266 |
Lxx_ = Lxx; |
||
267 |
} |
||
268 |
|||
269 |
template <typename Scalar> |
||
270 |
void ActionModelLQRTpl<Scalar>::set_Lxu(const MatrixXs& Lxu) { |
||
271 |
if (static_cast<std::size_t>(Lxu.rows()) != state_->get_nx() || |
||
272 |
static_cast<std::size_t>(Lxu.cols()) != nu_) { |
||
273 |
throw_pretty("Invalid argument: " |
||
274 |
<< "Lxu has wrong dimension (it should be " + |
||
275 |
std::to_string(state_->get_nx()) + "," + |
||
276 |
std::to_string(nu_) + ")"); |
||
277 |
} |
||
278 |
Lxu_ = Lxu; |
||
279 |
} |
||
280 |
|||
281 |
template <typename Scalar> |
||
282 |
void ActionModelLQRTpl<Scalar>::set_Luu(const MatrixXs& Luu) { |
||
283 |
if (static_cast<std::size_t>(Luu.rows()) != nu_ || |
||
284 |
static_cast<std::size_t>(Luu.cols()) != nu_) { |
||
285 |
throw_pretty("Invalid argument: " |
||
286 |
<< "Fq has wrong dimension (it should be " + |
||
287 |
std::to_string(nu_) + "," + std::to_string(nu_) + ")"); |
||
288 |
} |
||
289 |
Luu_ = Luu; |
||
290 |
} |
||
291 |
|||
292 |
} // namespace crocoddyl |
Generated by: GCOVR (Version 4.2) |