WPILibC++ 2027.0.0-alpha-5
Loading...
Searching...
No Matches
variable.hpp
Go to the documentation of this file.
1// Copyright (c) Sleipnir contributors
2
3#pragma once
4
5#include <algorithm>
6#include <concepts>
7#include <initializer_list>
8#include <source_location>
9#include <utility>
10#include <vector>
11
12#include <Eigen/Core>
13#include <gch/small_vector.hpp>
14
20
21#ifndef SLEIPNIR_DISABLE_DIAGNOSTICS
23#endif
24
25namespace slp {
26
27// Forward declarations for friend declarations in Variable
28
29namespace detail {
30
31template <typename Scalar>
33
34} // namespace detail
35
36template <typename Scalar, int UpLo = Eigen::Lower | Eigen::Upper>
37 requires(UpLo == Eigen::Lower) || (UpLo == (Eigen::Lower | Eigen::Upper))
38class Hessian;
39
40template <typename Scalar>
41class Jacobian;
42
43/// An autodiff variable pointing to an expression node.
44///
45/// @tparam Scalar_ Scalar type.
46template <typename Scalar_>
47class Variable : public SleipnirBase {
48 public:
49 /// Scalar type alias.
50 using Scalar = Scalar_;
51
52 /// Constructs a linear Variable with a value of zero.
53 Variable() = default;
54
55 /// Constructs an empty Variable.
56 explicit Variable(std::nullptr_t) : expr{nullptr} {}
57
58 /// Constructs a Variable from a scalar type.
59 ///
60 /// @param value The value of the Variable.
61 // NOLINTNEXTLINE (google-explicit-constructor)
63 requires(!MatrixLike<Scalar>)
64 : expr{detail::make_expression_ptr<detail::ConstantExpression<Scalar>>(
65 value)} {}
66
67 /// Constructs a Variable from a scalar type.
68 ///
69 /// @param value The value of the Variable.
70 // NOLINTNEXTLINE (google-explicit-constructor)
72 slp_assert(value.rows() == 1 && value.cols() == 1);
73 }
74
75 /// Constructs a Variable from a floating-point type.
76 ///
77 /// @param value The value of the Variable.
78 // NOLINTNEXTLINE (google-explicit-constructor)
79 Variable(std::floating_point auto value)
80 : expr{detail::make_expression_ptr<detail::ConstantExpression<Scalar>>(
81 Scalar(value))} {}
82
83 /// Constructs a Variable from an integral type.
84 ///
85 /// @param value The value of the Variable.
86 // NOLINTNEXTLINE (google-explicit-constructor)
87 Variable(std::integral auto value)
88 : expr{detail::make_expression_ptr<detail::ConstantExpression<Scalar>>(
89 Scalar(value))} {}
90
91 /// Constructs a Variable pointing to the specified expression.
92 ///
93 /// @param expr The autodiff variable.
94 explicit Variable(const detail::ExpressionPtr<Scalar>& expr) : expr{expr} {}
95
96 /// Constructs a Variable pointing to the specified expression.
97 ///
98 /// @param expr The autodiff variable.
100 : expr{std::move(expr)} {}
101
102 /// Assignment operator for scalar.
103 ///
104 /// @param value The value of the Variable.
105 /// @return This variable.
107 expr =
109 m_graph_initialized = false;
110
111 return *this;
112 }
113
114 /// Sets Variable's internal value.
115 ///
116 /// @param value The value of the Variable.
118#ifndef SLEIPNIR_DISABLE_DIAGNOSTICS
119 // We only need to check the first argument since unary and binary operators
120 // both use it
121 if (expr->args[0] != nullptr) {
122 auto location = std::source_location::current();
124 stderr,
125 "WARNING: {}:{}: {}: Modified the value of a dependent variable",
126 location.file_name(), location.line(), location.function_name());
127 }
128#endif
129 expr->val = Scalar(value);
130 }
131
132 /// Returns the value of this variable.
133 ///
134 /// @return The value of this variable.
136 if (!m_graph_initialized) {
137 m_graph = detail::topological_sort(expr);
138 m_graph_initialized = true;
139 }
140 detail::update_values(m_graph);
141
142 return Scalar(expr->val);
143 }
144
145 /// Returns the type of this expression (constant, linear, quadratic, or
146 /// nonlinear).
147 ///
148 /// @return The type of this expression.
149 ExpressionType type() const { return expr->type(); }
150
151 /// Variable-scalar multiplication operator.
152 ///
153 /// @param lhs Operator left-hand side.
154 /// @param rhs Operator right-hand side.
155 /// @return Result of multiplication.
156 template <ScalarLike LHS, SleipnirScalarLike<Scalar> RHS>
157 friend Variable<Scalar> operator*(const LHS& lhs, const RHS& rhs) {
158 return Variable{Variable<Scalar>{lhs}.expr * rhs.expr};
159 }
160
161 /// Variable-scalar multiplication operator.
162 ///
163 /// @param lhs Operator left-hand side.
164 /// @param rhs Operator right-hand side.
165 /// @return Result of multiplication.
166 template <SleipnirScalarLike<Scalar> LHS, ScalarLike RHS>
167 friend Variable<Scalar> operator*(const LHS& lhs, const RHS& rhs) {
168 return Variable{lhs.expr * Variable<Scalar>{rhs}.expr};
169 }
170
171 /// Variable-scalar multiplication operator.
172 ///
173 /// @param lhs Operator left-hand side.
174 /// @param rhs Operator right-hand side.
175 /// @return Result of multiplication.
177 const Variable<Scalar>& rhs) {
178 return Variable{lhs.expr * rhs.expr};
179 }
180
181 /// Variable-Variable compound multiplication operator.
182 ///
183 /// @param rhs Operator right-hand side.
184 /// @return Result of multiplication.
186 *this = *this * rhs;
187 return *this;
188 }
189
190 /// Variable-Variable division operator.
191 ///
192 /// @param lhs Operator left-hand side.
193 /// @param rhs Operator right-hand side.
194 /// @return Result of division.
196 const Variable<Scalar>& rhs) {
197 return Variable{lhs.expr / rhs.expr};
198 }
199
200 /// Variable-Variable compound division operator.
201 ///
202 /// @param rhs Operator right-hand side.
203 /// @return Result of division.
205 *this = *this / rhs;
206 return *this;
207 }
208
209 /// Variable-Variable addition operator.
210 ///
211 /// @param lhs Operator left-hand side.
212 /// @param rhs Operator right-hand side.
213 /// @return Result of addition.
215 const Variable<Scalar>& rhs) {
216 return Variable{lhs.expr + rhs.expr};
217 }
218
219 /// Variable-Variable compound addition operator.
220 ///
221 /// @param rhs Operator right-hand side.
222 /// @return Result of addition.
224 *this = *this + rhs;
225 return *this;
226 }
227
228 /// Variable-Variable subtraction operator.
229 ///
230 /// @param lhs Operator left-hand side.
231 /// @param rhs Operator right-hand side.
232 /// @return Result of subtraction.
234 const Variable<Scalar>& rhs) {
235 return Variable{lhs.expr - rhs.expr};
236 }
237
238 /// Variable-Variable compound subtraction operator.
239 ///
240 /// @param rhs Operator right-hand side.
241 /// @return Result of subtraction.
243 *this = *this - rhs;
244 return *this;
245 }
246
247 /// Unary minus operator.
248 ///
249 /// @param lhs Operand for unary minus.
251 return Variable{-lhs.expr};
252 }
253
254 /// Unary plus operator.
255 ///
256 /// @param lhs Operand for unary plus.
258 return Variable{+lhs.expr};
259 }
260
261 private:
262 /// The expression node
265
266 /// Used to update the value of this variable based on the values of its
267 /// dependent variables
269
270 /// Used for lazy initialization of m_graph
271 bool m_graph_initialized = false;
272
273 template <typename Scalar>
275 template <typename Scalar>
277 template <typename Scalar>
279 template <typename Scalar>
281 template <typename Scalar>
282 friend Variable<Scalar> atan2(const ScalarLike auto& y,
283 const Variable<Scalar>& x);
284 template <typename Scalar>
286 const ScalarLike auto& x);
287 template <typename Scalar>
289 const Variable<Scalar>& x);
290 template <typename Scalar>
292 template <typename Scalar>
294 template <typename Scalar>
296 template <typename Scalar>
298 template <typename Scalar>
300 template <typename Scalar>
301 friend Variable<Scalar> hypot(const ScalarLike auto& x,
302 const Variable<Scalar>& y);
303 template <typename Scalar>
305 const ScalarLike auto& y);
306 template <typename Scalar>
308 const Variable<Scalar>& y);
309 template <typename Scalar>
311 template <typename Scalar>
313 template <typename Scalar>
314 friend Variable<Scalar> max(const ScalarLike auto& a,
315 const Variable<Scalar>& b);
316 template <typename Scalar>
318 const ScalarLike auto& b);
319 template <typename Scalar>
321 const Variable<Scalar>& b);
322 template <typename Scalar>
323 friend Variable<Scalar> min(const ScalarLike auto& a,
324 const Variable<Scalar>& b);
325 template <typename Scalar>
327 const ScalarLike auto& b);
328 template <typename Scalar>
330 const Variable<Scalar>& b);
331 template <typename Scalar>
332 friend Variable<Scalar> pow(const ScalarLike auto& base,
333 const Variable<Scalar>& power);
334 template <typename Scalar>
336 const ScalarLike auto& power);
337 template <typename Scalar>
339 const Variable<Scalar>& power);
340 template <typename Scalar>
342 template <typename Scalar>
344 template <typename Scalar>
346 template <typename Scalar>
348 template <typename Scalar>
350 template <typename Scalar>
352 template <typename Scalar>
354 const Variable<Scalar>& y,
355 const Variable<Scalar>& z);
356
358 template <typename Scalar, int UpLo>
359 requires(UpLo == Eigen::Lower) || (UpLo == (Eigen::Lower | Eigen::Upper))
360 friend class Hessian;
361 template <typename Scalar>
362 friend class Jacobian;
363};
364
365template <template <typename> typename T, typename Scalar>
366 requires SleipnirMatrixLike<T<Scalar>, Scalar>
368
369template <std::floating_point T>
371
372template <std::integral T>
374
375/// abs() for Variables.
376///
377/// @tparam Scalar Scalar type.
378/// @param x The argument.
379template <typename Scalar>
381 return Variable{detail::abs(x.expr)};
382}
383
384/// acos() for Variables.
385///
386/// @tparam Scalar Scalar type.
387/// @param x The argument.
388template <typename Scalar>
390 return Variable{detail::acos(x.expr)};
391}
392
393/// asin() for Variables.
394///
395/// @tparam Scalar Scalar type.
396/// @param x The argument.
397template <typename Scalar>
399 return Variable{detail::asin(x.expr)};
400}
401
402/// atan() for Variables.
403///
404/// @tparam Scalar Scalar type.
405/// @param x The argument.
406template <typename Scalar>
408 return Variable{detail::atan(x.expr)};
409}
410
411/// atan2() for Variables.
412///
413/// @tparam Scalar Scalar type.
414/// @param y The y argument.
415/// @param x The x argument.
416template <typename Scalar>
418 return Variable{detail::atan2(Variable<Scalar>(y).expr, x.expr)};
419}
420
421/// atan2() for Variables.
422///
423/// @tparam Scalar Scalar type.
424/// @param y The y argument.
425/// @param x The x argument.
426template <typename Scalar>
428 return Variable{detail::atan2(y.expr, Variable<Scalar>(x).expr)};
429}
430
431/// atan2() for Variables.
432///
433/// @tparam Scalar Scalar type.
434/// @param y The y argument.
435/// @param x The x argument.
436template <typename Scalar>
438 return Variable{detail::atan2(y.expr, x.expr)};
439}
440
441/// cbrt() for Variables.
442///
443/// @tparam Scalar Scalar type.
444/// @param x The argument.
445template <typename Scalar>
447 return Variable{detail::cbrt(x.expr)};
448}
449
450/// cos() for Variables.
451///
452/// @tparam Scalar Scalar type.
453/// @param x The argument.
454template <typename Scalar>
456 return Variable{detail::cos(x.expr)};
457}
458
459/// cosh() for Variables.
460///
461/// @tparam Scalar Scalar type.
462/// @param x The argument.
463template <typename Scalar>
465 return Variable{detail::cosh(x.expr)};
466}
467
468/// erf() for Variables.
469///
470/// @tparam Scalar Scalar type.
471/// @param x The argument.
472template <typename Scalar>
474 return Variable{detail::erf(x.expr)};
475}
476
477/// exp() for Variables.
478///
479/// @tparam Scalar Scalar type.
480/// @param x The argument.
481template <typename Scalar>
483 return Variable{detail::exp(x.expr)};
484}
485
486/// hypot() for Variables.
487///
488/// @tparam Scalar Scalar type.
489/// @param x The x argument.
490/// @param y The y argument.
491template <typename Scalar>
493 return Variable{detail::hypot(Variable<Scalar>(x).expr, y.expr)};
494}
495
496/// hypot() for Variables.
497///
498/// @tparam Scalar Scalar type.
499/// @param x The x argument.
500/// @param y The y argument.
501template <typename Scalar>
503 return Variable{detail::hypot(x.expr, Variable<Scalar>(y).expr)};
504}
505
506/// hypot() for Variables.
507///
508/// @tparam Scalar Scalar type.
509/// @param x The x argument.
510/// @param y The y argument.
511template <typename Scalar>
513 return Variable{detail::hypot(x.expr, y.expr)};
514}
515
516/// log() for Variables.
517///
518/// @tparam Scalar Scalar type.
519/// @param x The argument.
520template <typename Scalar>
522 return Variable{detail::log(x.expr)};
523}
524
525/// log10() for Variables.
526///
527/// @tparam Scalar Scalar type.
528/// @param x The argument.
529template <typename Scalar>
531 return Variable{detail::log10(x.expr)};
532}
533
534/// max() for Variables.
535///
536/// Returns the greater of a and b. If the values are equivalent, returns a.
537///
538/// @tparam Scalar Scalar type.
539/// @param a The a argument.
540/// @param b The b argument.
541template <typename Scalar>
543 return Variable{detail::max(Variable<Scalar>(a).expr, b.expr)};
544}
545
546/// max() for Variables.
547///
548/// Returns the greater of a and b. If the values are equivalent, returns a.
549///
550/// @tparam Scalar Scalar type.
551/// @param a The a argument.
552/// @param b The b argument.
553template <typename Scalar>
555 return Variable{detail::max(a.expr, Variable<Scalar>(b).expr)};
556}
557
558/// max() for Variables.
559///
560/// Returns the greater of a and b. If the values are equivalent, returns a.
561///
562/// @tparam Scalar Scalar type.
563/// @param a The a argument.
564/// @param b The b argument.
565template <typename Scalar>
567 return Variable{detail::max(a.expr, b.expr)};
568}
569
570/// min() for Variables.
571///
572/// Returns the lesser of a and b. If the values are equivalent, returns a.
573///
574/// @tparam Scalar Scalar type.
575/// @param a The a argument.
576/// @param b The b argument.
577template <typename Scalar>
579 return Variable{detail::min(Variable<Scalar>(a).expr, b.expr)};
580}
581
582/// min() for Variables.
583///
584/// Returns the lesser of a and b. If the values are equivalent, returns a.
585///
586/// @tparam Scalar Scalar type.
587/// @param a The a argument.
588/// @param b The b argument.
589template <typename Scalar>
591 return Variable{detail::min(a.expr, Variable<Scalar>(b).expr)};
592}
593
594/// min() for Variables.
595///
596/// Returns the lesser of a and b. If the values are equivalent, returns a.
597///
598/// @tparam Scalar Scalar type.
599/// @param a The a argument.
600/// @param b The b argument.
601template <typename Scalar>
603 return Variable{detail::min(a.expr, b.expr)};
604}
605
606/// pow() for Variables.
607///
608/// @tparam Scalar Scalar type.
609/// @param base The base.
610/// @param power The power.
611template <typename Scalar>
613 const Variable<Scalar>& power) {
614 return Variable{detail::pow(Variable<Scalar>(base).expr, power.expr)};
615}
616
617/// pow() for Variables.
618///
619/// @tparam Scalar Scalar type.
620/// @param base The base.
621/// @param power The power.
622template <typename Scalar>
624 const ScalarLike auto& power) {
625 return Variable{detail::pow(base.expr, Variable<Scalar>(power).expr)};
626}
627
628/// pow() for Variables.
629///
630/// @tparam Scalar Scalar type.
631/// @param base The base.
632/// @param power The power.
633template <typename Scalar>
635 const Variable<Scalar>& power) {
636 return Variable{detail::pow(base.expr, power.expr)};
637}
638
639/// sign() for Variables.
640///
641/// @tparam Scalar Scalar type.
642/// @param x The argument.
643template <typename Scalar>
645 return Variable{detail::sign(x.expr)};
646}
647
648/// sin() for Variables.
649///
650/// @tparam Scalar Scalar type.
651/// @param x The argument.
652template <typename Scalar>
654 return Variable{detail::sin(x.expr)};
655}
656
657/// sinh() for Variables.
658///
659/// @tparam Scalar Scalar type.
660/// @param x The argument.
661template <typename Scalar>
663 return Variable{detail::sinh(x.expr)};
664}
665
666/// sqrt() for Variables.
667///
668/// @tparam Scalar Scalar type.
669/// @param x The argument.
670template <typename Scalar>
672 return Variable{detail::sqrt(x.expr)};
673}
674
675/// tan() for Variables.
676///
677/// @tparam Scalar Scalar type.
678/// @param x The argument.
679template <typename Scalar>
681 return Variable{detail::tan(x.expr)};
682}
683
684/// tanh() for Variables.
685///
686/// @tparam Scalar Scalar type.
687/// @param x The argument.
688template <typename Scalar>
690 return Variable{detail::tanh(x.expr)};
691}
692
693/// hypot() for Variables.
694///
695/// @tparam Scalar Scalar type.
696/// @param x The x argument.
697/// @param y The y argument.
698/// @param z The z argument.
699template <typename Scalar>
701 const Variable<Scalar>& z) {
702 return Variable{sqrt(pow(x, 2) + pow(y, 2) + pow(z, 2))};
703}
704
705// The standard form for equality constraints is c(x) = 0, and the standard form
706// for inequality constraints is c(x) ≥ 0. make_constraints() takes constraints
707// of the form lhs = rhs or lhs ≥ rhs and converts them to lhs - rhs = 0 or
708// lhs - rhs ≥ 0.
709
710template <typename Scalar, ScalarLike LHS, ScalarLike RHS>
712auto make_constraints(LHS&& lhs, RHS&& rhs) {
714 constraints.emplace_back(lhs - rhs);
715
716 return constraints;
717}
718
719template <typename Scalar, ScalarLike LHS, MatrixLike RHS>
720 requires SleipnirScalarLike<LHS, Scalar> || SleipnirMatrixLike<RHS, Scalar>
721auto make_constraints(LHS&& lhs, RHS&& rhs) {
723 constraints.reserve(rhs.rows() * rhs.cols());
724
725 for (int row = 0; row < rhs.rows(); ++row) {
726 for (int col = 0; col < rhs.cols(); ++col) {
727 // Make right-hand side zero
728 constraints.emplace_back(lhs - rhs(row, col));
729 }
730 }
731
732 return constraints;
733}
734
735template <typename Scalar, MatrixLike LHS, ScalarLike RHS>
736 requires SleipnirMatrixLike<LHS, Scalar> || SleipnirScalarLike<RHS, Scalar>
737auto make_constraints(LHS&& lhs, RHS&& rhs) {
739 constraints.reserve(lhs.rows() * lhs.cols());
740
741 for (int row = 0; row < lhs.rows(); ++row) {
742 for (int col = 0; col < lhs.cols(); ++col) {
743 // Make right-hand side zero
744 constraints.emplace_back(lhs(row, col) - rhs);
745 }
746 }
747
748 return constraints;
749}
750
751template <typename Scalar, MatrixLike LHS, MatrixLike RHS>
752 requires SleipnirMatrixLike<LHS, Scalar> || SleipnirMatrixLike<RHS, Scalar>
753auto make_constraints(LHS&& lhs, RHS&& rhs) {
754 slp_assert(lhs.rows() == rhs.rows() && lhs.cols() == rhs.cols());
755
757 constraints.reserve(lhs.rows() * lhs.cols());
758
759 for (int row = 0; row < lhs.rows(); ++row) {
760 for (int col = 0; col < lhs.cols(); ++col) {
761 // Make right-hand side zero
762 constraints.emplace_back(lhs(row, col) - rhs(row, col));
763 }
764 }
765
766 return constraints;
767}
768
769/// A vector of equality constraints of the form cₑ(x) = 0.
770///
771/// @tparam Scalar Scalar type.
772template <typename Scalar>
774 /// A vector of scalar equality constraints.
776
777 /// Concatenates multiple equality constraints.
778 ///
779 /// @param equality_constraints The list of EqualityConstraints to
780 /// concatenate.
782 std::initializer_list<EqualityConstraints> equality_constraints) {
783 for (const auto& elem : equality_constraints) {
784 constraints.insert(constraints.end(), elem.constraints.begin(),
785 elem.constraints.end());
786 }
787 }
788
789 /// Concatenates multiple equality constraints.
790 ///
791 /// This overload is for Python bindings only.
792 ///
793 /// @param equality_constraints The list of EqualityConstraints to
794 /// concatenate.
796 const std::vector<EqualityConstraints>& equality_constraints) {
797 for (const auto& elem : equality_constraints) {
798 constraints.insert(constraints.end(), elem.constraints.begin(),
799 elem.constraints.end());
800 }
801 }
802
803 /// Constructs an equality constraint from a left and right side.
804 ///
805 /// The standard form for equality constraints is c(x) = 0. This function
806 /// takes a constraint of the form lhs = rhs and converts it to lhs - rhs = 0.
807 ///
808 /// @param lhs Left-hand side.
809 /// @param rhs Right-hand side.
810 template <typename LHS, typename RHS>
811 requires(ScalarLike<LHS> || MatrixLike<LHS>) &&
814 EqualityConstraints(LHS&& lhs, RHS&& rhs)
816
817 /// Implicit conversion operator to bool.
818 // NOLINTNEXTLINE (google-explicit-constructor)
819 operator bool() {
820 return std::ranges::all_of(constraints, [](auto& constraint) {
821 return constraint.value() == Scalar(0);
822 });
823 }
824};
825
826/// A vector of inequality constraints of the form cᵢ(x) ≥ 0.
827///
828/// @tparam Scalar Scalar type.
829template <typename Scalar>
831 /// A vector of scalar inequality constraints.
833
834 /// Concatenates multiple inequality constraints.
835 ///
836 /// @param inequality_constraints The list of InequalityConstraints to
837 /// concatenate.
839 std::initializer_list<InequalityConstraints> inequality_constraints) {
840 for (const auto& elem : inequality_constraints) {
841 constraints.insert(constraints.end(), elem.constraints.begin(),
842 elem.constraints.end());
843 }
844 }
845
846 /// Concatenates multiple inequality constraints.
847 ///
848 /// This overload is for Python bindings only.
849 ///
850 /// @param inequality_constraints The list of InequalityConstraints to
851 /// concatenate.
853 const std::vector<InequalityConstraints>& inequality_constraints) {
854 for (const auto& elem : inequality_constraints) {
855 constraints.insert(constraints.end(), elem.constraints.begin(),
856 elem.constraints.end());
857 }
858 }
859
860 /// Constructs an inequality constraint from a left and right side.
861 ///
862 /// The standard form for inequality constraints is c(x) ≥ 0. This function
863 /// takes a constraints of the form lhs ≥ rhs and converts it to lhs - rhs ≥
864 /// 0.
865 ///
866 /// @param lhs Left-hand side.
867 /// @param rhs Right-hand side.
868 template <typename LHS, typename RHS>
869 requires(ScalarLike<LHS> || MatrixLike<LHS>) &&
872 InequalityConstraints(LHS&& lhs, RHS&& rhs)
874
875 /// Implicit conversion operator to bool.
876 // NOLINTNEXTLINE (google-explicit-constructor)
877 operator bool() {
878 return std::ranges::all_of(constraints, [](auto& constraint) {
879 return constraint.value() >= Scalar(0);
880 });
881 }
882};
883
884/// Equality operator that returns an equality constraint for two Variables.
885///
886/// @param lhs Left-hand side.
887/// @param rhs Left-hand side.
888template <typename LHS, typename RHS>
889 requires(ScalarLike<LHS> || MatrixLike<LHS>) && SleipnirType<LHS> &&
890 (ScalarLike<RHS> || MatrixLike<RHS>) && (!SleipnirType<RHS>)
891auto operator==(LHS&& lhs, RHS&& rhs) {
893}
894
895/// Equality operator that returns an equality constraint for two Variables.
896///
897/// @param lhs Left-hand side.
898/// @param rhs Left-hand side.
899template <typename LHS, typename RHS>
900 requires(ScalarLike<LHS> || MatrixLike<LHS>) && (!SleipnirType<LHS>) &&
901 (ScalarLike<RHS> || MatrixLike<RHS>) && SleipnirType<RHS>
902auto operator==(LHS&& lhs, RHS&& rhs) {
904}
905
906/// Equality operator that returns an equality constraint for two Variables.
907///
908/// @param lhs Left-hand side.
909/// @param rhs Left-hand side.
910template <typename LHS, typename RHS>
911 requires(ScalarLike<LHS> || MatrixLike<LHS>) && SleipnirType<LHS> &&
912 (ScalarLike<RHS> || MatrixLike<RHS>) && SleipnirType<RHS>
913auto operator==(LHS&& lhs, RHS&& rhs) {
915}
916
917/// Less-than comparison operator that returns an inequality constraint for two
918/// Variables.
919///
920/// @param lhs Left-hand side.
921/// @param rhs Left-hand side.
922template <typename LHS, typename RHS>
923 requires(ScalarLike<LHS> || MatrixLike<LHS>) &&
924 (ScalarLike<RHS> || MatrixLike<RHS>) &&
925 (SleipnirType<LHS> || SleipnirType<RHS>)
926auto operator<(LHS&& lhs, RHS&& rhs) {
927 return rhs >= lhs;
928}
929
930/// Less-than-or-equal-to comparison operator that returns an inequality
931/// constraint for two Variables.
932///
933/// @param lhs Left-hand side.
934/// @param rhs Left-hand side.
935template <typename LHS, typename RHS>
936 requires(ScalarLike<LHS> || MatrixLike<LHS>) &&
937 (ScalarLike<RHS> || MatrixLike<RHS>) &&
938 (SleipnirType<LHS> || SleipnirType<RHS>)
939auto operator<=(LHS&& lhs, RHS&& rhs) {
940 return rhs >= lhs;
941}
942
943/// Greater-than comparison operator that returns an inequality constraint for
944/// two Variables.
945///
946/// @param lhs Left-hand side.
947/// @param rhs Left-hand side.
948template <typename LHS, typename RHS>
949 requires(ScalarLike<LHS> || MatrixLike<LHS>) &&
950 (ScalarLike<RHS> || MatrixLike<RHS>) &&
951 (SleipnirType<LHS> || SleipnirType<RHS>)
952auto operator>(LHS&& lhs, RHS&& rhs) {
953 return lhs >= rhs;
954}
955
956/// Greater-than-or-equal-to comparison operator that returns an inequality
957/// constraint for two Variables.
958///
959/// @param lhs Left-hand side.
960/// @param rhs Left-hand side.
961template <typename LHS, typename RHS>
962 requires(ScalarLike<LHS> || MatrixLike<LHS>) && SleipnirType<LHS> &&
963 (ScalarLike<RHS> || MatrixLike<RHS>) && (!SleipnirType<RHS>)
964auto operator>=(LHS&& lhs, RHS&& rhs) {
966}
967
968/// Greater-than-or-equal-to comparison operator that returns an inequality
969/// constraint for two Variables.
970///
971/// @param lhs Left-hand side.
972/// @param rhs Left-hand side.
973template <typename LHS, typename RHS>
974 requires(ScalarLike<LHS> || MatrixLike<LHS>) && (!SleipnirType<LHS>) &&
975 (ScalarLike<RHS> || MatrixLike<RHS>) && SleipnirType<RHS>
976auto operator>=(LHS&& lhs, RHS&& rhs) {
978}
979
980/// Greater-than-or-equal-to comparison operator that returns an inequality
981/// constraint for two Variables.
982///
983/// @param lhs Left-hand side.
984/// @param rhs Left-hand side.
985template <typename LHS, typename RHS>
986 requires(ScalarLike<LHS> || MatrixLike<LHS>) && SleipnirType<LHS> &&
987 (ScalarLike<RHS> || MatrixLike<RHS>) && SleipnirType<RHS>
988auto operator>=(LHS&& lhs, RHS&& rhs) {
990}
991
992/// Helper function for creating bound constraints.
993///
994/// @param l Lower bound.
995/// @param x Variable to bound.
996/// @param u Upper bound.
997template <typename L, typename X, typename U>
998 requires(ScalarLike<L> || MatrixLike<L>) && SleipnirType<X> &&
999 (ScalarLike<U> || MatrixLike<U>)
1000auto bounds(L&& l, X&& x, U&& u) {
1001 return InequalityConstraints{l <= x, x <= u};
1002}
1003
1004} // namespace slp
1005
1006namespace Eigen {
1007
1008/// NumTraits specialization that allows instantiating Eigen types with
1009/// Variable.
1010///
1011/// @tparam Scalar Scalar type.
1012template <typename Scalar>
1013struct NumTraits<slp::Variable<Scalar>> : NumTraits<Scalar> {
1014 /// Real type.
1016 /// Non-integer type.
1018 /// Nested type.
1020
1021 /// Is complex.
1022 static constexpr int IsComplex = 0;
1023 /// Is integer.
1024 static constexpr int IsInteger = 0;
1025 /// Is signed.
1026 static constexpr int IsSigned = 1;
1027 /// Require initialization.
1028 static constexpr int RequireInitialization = 1;
1029 /// Read cost.
1030 static constexpr int ReadCost = 1;
1031 /// Add cost.
1032 static constexpr int AddCost = 3;
1033 /// Multiply cost.
1034 static constexpr int MulCost = 3;
1035};
1036
1037} // namespace Eigen
#define slp_assert(condition)
Aborts in C++.
Definition assert.hpp:25
sign
Definition base.h:689
This class calculates the Hessian of a variable with respect to a vector of variables.
Definition hessian.hpp:28
This class calculates the Jacobian of a vector of variables with respect to a vector of variables.
Definition jacobian.hpp:28
Marker interface for concepts to determine whether a given scalar or matrix type belongs to Sleipnir.
Definition sleipnir_base.hpp:9
An autodiff variable pointing to an expression node.
Definition variable.hpp:47
ExpressionType type() const
Returns the type of this expression (constant, linear, quadratic, or nonlinear).
Definition variable.hpp:149
friend Variable< Scalar > operator*(const LHS &lhs, const RHS &rhs)
Variable-scalar multiplication operator.
Definition variable.hpp:157
Variable(const detail::ExpressionPtr< Scalar > &expr)
Constructs a Variable pointing to the specified expression.
Definition variable.hpp:94
friend Variable< Scalar > pow(const ScalarLike auto &base, const Variable< Scalar > &power)
friend Variable< Scalar > abs(const Variable< Scalar > &x)
friend class Jacobian
Definition variable.hpp:362
friend Variable< Scalar > hypot(const Variable< Scalar > &x, const ScalarLike auto &y)
Variable< Scalar > & operator/=(const Variable< Scalar > &rhs)
Variable-Variable compound division operator.
Definition variable.hpp:204
friend Variable< Scalar > log(const Variable< Scalar > &x)
friend Variable< Scalar > erf(const Variable< Scalar > &x)
friend Variable< Scalar > atan(const Variable< Scalar > &x)
friend Variable< Scalar > min(const ScalarLike auto &a, const Variable< Scalar > &b)
friend Variable< Scalar > max(const ScalarLike auto &a, const Variable< Scalar > &b)
Variable< Scalar > & operator*=(const Variable< Scalar > &rhs)
Variable-Variable compound multiplication operator.
Definition variable.hpp:185
friend Variable< Scalar > asin(const Variable< Scalar > &x)
friend Variable< Scalar > exp(const Variable< Scalar > &x)
friend Variable< Scalar > hypot(const ScalarLike auto &x, const Variable< Scalar > &y)
friend Variable< Scalar > sin(const Variable< Scalar > &x)
friend Variable< Scalar > operator+(const Variable< Scalar > &lhs, const Variable< Scalar > &rhs)
Variable-Variable addition operator.
Definition variable.hpp:214
friend Variable< Scalar > atan2(const Variable< Scalar > &y, const Variable< Scalar > &x)
friend class Hessian
Definition variable.hpp:360
void set_value(Scalar value)
Sets Variable's internal value.
Definition variable.hpp:117
friend Variable< Scalar > operator/(const Variable< Scalar > &lhs, const Variable< Scalar > &rhs)
Variable-Variable division operator.
Definition variable.hpp:195
friend Variable< Scalar > log10(const Variable< Scalar > &x)
friend Variable< Scalar > atan2(const Variable< Scalar > &y, const ScalarLike auto &x)
Variable(std::floating_point auto value)
Constructs a Variable from a floating-point type.
Definition variable.hpp:79
friend Variable< Scalar > pow(const Variable< Scalar > &base, const ScalarLike auto &power)
friend Variable< Scalar > cos(const Variable< Scalar > &x)
friend Variable< Scalar > sign(const Variable< Scalar > &x)
friend Variable< Scalar > max(const Variable< Scalar > &a, const ScalarLike auto &b)
friend Variable< Scalar > operator+(const Variable< Scalar > &lhs)
Unary plus operator.
Definition variable.hpp:257
friend Variable< Scalar > tanh(const Variable< Scalar > &x)
Variable(Scalar value)
Constructs a Variable from a scalar type.
Definition variable.hpp:62
friend Variable< Scalar > sinh(const Variable< Scalar > &x)
friend Variable< Scalar > pow(const Variable< Scalar > &base, const Variable< Scalar > &power)
Variable< Scalar > & operator=(ScalarLike auto value)
Assignment operator for scalar.
Definition variable.hpp:106
friend Variable< Scalar > cbrt(const Variable< Scalar > &x)
friend Variable< Scalar > sqrt(const Variable< Scalar > &x)
friend Variable< Scalar > atan2(const ScalarLike auto &y, const Variable< Scalar > &x)
Variable()=default
Constructs a linear Variable with a value of zero.
friend Variable< Scalar > operator-(const Variable< Scalar > &lhs)
Unary minus operator.
Definition variable.hpp:250
friend Variable< Scalar > operator*(const Variable< Scalar > &lhs, const Variable< Scalar > &rhs)
Variable-scalar multiplication operator.
Definition variable.hpp:176
friend Variable< Scalar > acos(const Variable< Scalar > &x)
friend Variable< Scalar > cosh(const Variable< Scalar > &x)
Variable(std::integral auto value)
Constructs a Variable from an integral type.
Definition variable.hpp:87
friend Variable< Scalar > hypot(const Variable< Scalar > &x, const Variable< Scalar > &y)
Variable(detail::ExpressionPtr< Scalar > &&expr)
Constructs a Variable pointing to the specified expression.
Definition variable.hpp:99
Variable(SleipnirMatrixLike< Scalar > auto value)
Constructs a Variable from a scalar type.
Definition variable.hpp:71
Variable< Scalar > & operator+=(const Variable< Scalar > &rhs)
Variable-Variable compound addition operator.
Definition variable.hpp:223
Scalar Scalar
Definition variable.hpp:50
friend Variable< Scalar > tan(const Variable< Scalar > &x)
Scalar value()
Definition variable.hpp:135
Variable< Scalar > & operator-=(const Variable< Scalar > &rhs)
Variable-Variable compound subtraction operator.
Definition variable.hpp:242
friend Variable< Scalar > operator-(const Variable< Scalar > &lhs, const Variable< Scalar > &rhs)
Variable-Variable subtraction operator.
Definition variable.hpp:233
friend Variable< Scalar > min(const Variable< Scalar > &a, const Variable< Scalar > &b)
friend Variable< Scalar > max(const Variable< Scalar > &a, const Variable< Scalar > &b)
friend Variable< Scalar > min(const Variable< Scalar > &a, const ScalarLike auto &b)
Variable(std::nullptr_t)
Constructs an empty Variable.
Definition variable.hpp:56
This class is an adapter type that performs value updates of an expression graph, generates a gradien...
Definition gradient_expression_graph.hpp:25
Definition concepts.hpp:18
Definition concepts.hpp:24
Definition concepts.hpp:33
Definition concepts.hpp:38
Definition concepts.hpp:15
Definition variable.hpp:1006
Converts a string literal into a format string that will be parsed at compile time and converted into...
Definition printf.h:50
@ sign
Definition base.h:1467
wpi::util::SmallVector< T > small_vector
Definition small_vector.hpp:10
Definition expression_graph.hpp:11
ExpressionPtr< Scalar > cosh(const ExpressionPtr< Scalar > &x)
cosh() for Expressions.
Definition expression.hpp:1164
ExpressionPtr< Scalar > cos(const ExpressionPtr< Scalar > &x)
cos() for Expressions.
Definition expression.hpp:1110
ExpressionPtr< Scalar > cbrt(const ExpressionPtr< Scalar > &x)
cbrt() for Expressions.
Definition expression.hpp:554
ExpressionPtr< Scalar > sin(const ExpressionPtr< Scalar > &x)
sin() for Expressions.
Definition expression.hpp:1825
ExpressionPtr< Scalar > hypot(const ExpressionPtr< Scalar > &x, const ExpressionPtr< Scalar > &y)
hypot() for Expressions.
Definition expression.hpp:1347
ExpressionPtr< Scalar > pow(const ExpressionPtr< Scalar > &base, const ExpressionPtr< Scalar > &power)
pow() for Expressions.
Definition expression.hpp:1704
ExpressionPtr< Scalar > sqrt(const ExpressionPtr< Scalar > &x)
sqrt() for Expressions.
Definition expression.hpp:1935
ExpressionPtr< Scalar > sinh(const ExpressionPtr< Scalar > &x)
sinh() for Expressions.
Definition expression.hpp:1880
void update_values(const gch::small_vector< Expression< Scalar > * > &list)
Updates the values of all nodes in this graph based on the values of their dependent nodes.
Definition expression_graph.hpp:77
ExpressionPtr< Scalar > min(const ExpressionPtr< Scalar > &a, const ExpressionPtr< Scalar > &b)
min() for Expressions.
Definition expression.hpp:1621
ExpressionPtr< Scalar > erf(const ExpressionPtr< Scalar > &x)
erf() for Expressions.
Definition expression.hpp:1220
ExpressionPtr< Scalar > tan(const ExpressionPtr< Scalar > &x)
tan() for Expressions.
Definition expression.hpp:1994
ExpressionPtr< Scalar > abs(const ExpressionPtr< Scalar > &x)
abs() for Expressions.
Definition expression.hpp:822
ExpressionPtr< Scalar > tanh(const ExpressionPtr< Scalar > &x)
tanh() for Expressions.
Definition expression.hpp:2052
ExpressionPtr< Scalar > exp(const ExpressionPtr< Scalar > &x)
exp() for Expressions.
Definition expression.hpp:1275
ExpressionPtr< Scalar > asin(const ExpressionPtr< Scalar > &x)
asin() for Expressions.
Definition expression.hpp:931
ExpressionPtr< Scalar > log(const ExpressionPtr< Scalar > &x)
log() for Expressions.
Definition expression.hpp:1403
ExpressionPtr< Scalar > acos(const ExpressionPtr< Scalar > &x)
acos() for Expressions.
Definition expression.hpp:877
gch::small_vector< Expression< Scalar > * > topological_sort(const ExpressionPtr< Scalar > &root)
Generates a topological sort of an expression graph from parent to child.
Definition expression_graph.hpp:20
ExpressionPtr< Scalar > max(const ExpressionPtr< Scalar > &a, const ExpressionPtr< Scalar > &b)
max() for Expressions.
Definition expression.hpp:1541
ExpressionPtr< Scalar > atan(const ExpressionPtr< Scalar > &x)
atan() for Expressions.
Definition expression.hpp:985
IntrusiveSharedPtr< Expression< Scalar > > ExpressionPtr
Typedef for intrusive shared pointer to Expression.
Definition expression.hpp:43
ExpressionPtr< Scalar > atan2(const ExpressionPtr< Scalar > &y, const ExpressionPtr< Scalar > &x)
atan2() for Expressions.
Definition expression.hpp:1052
static ExpressionPtr< typename T::Scalar > make_expression_ptr(Args &&... args)
Creates an intrusive shared pointer to an expression from the global pool allocator.
Definition expression.hpp:51
ExpressionPtr< Scalar > log10(const ExpressionPtr< Scalar > &x)
log10() for Expressions.
Definition expression.hpp:1457
Definition to_underlying.hpp:7
ExpressionType
Expression type.
Definition expression_type.hpp:16
auto operator==(LHS &&lhs, RHS &&rhs)
Equality operator that returns an equality constraint for two Variables.
Definition variable.hpp:891
auto make_constraints(LHS &&lhs, RHS &&rhs)
Definition variable.hpp:712
auto bounds(L &&l, X &&x, U &&u)
Helper function for creating bound constraints.
Definition variable.hpp:1000
auto operator>=(LHS &&lhs, RHS &&rhs)
Greater-than-or-equal-to comparison operator that returns an inequality constraint for two Variables.
Definition variable.hpp:964
void println(fmt::format_string< T... > fmt, T &&... args)
Wrapper around fmt::println() that squelches write failure exceptions.
Definition print.hpp:37
Definition StringMap.hpp:773
static constexpr int IsInteger
Is integer.
Definition variable.hpp:1024
static constexpr int AddCost
Add cost.
Definition variable.hpp:1032
static constexpr int ReadCost
Read cost.
Definition variable.hpp:1030
slp::Variable< Scalar > Real
Real type.
Definition variable.hpp:1015
static constexpr int RequireInitialization
Require initialization.
Definition variable.hpp:1028
static constexpr int MulCost
Multiply cost.
Definition variable.hpp:1034
static constexpr int IsComplex
Is complex.
Definition variable.hpp:1022
static constexpr int IsSigned
Is signed.
Definition variable.hpp:1026
slp::Variable< Scalar > Nested
Nested type.
Definition variable.hpp:1019
slp::Variable< Scalar > NonInteger
Non-integer type.
Definition variable.hpp:1017
A vector of equality constraints of the form cₑ(x) = 0.
Definition variable.hpp:773
EqualityConstraints(LHS &&lhs, RHS &&rhs)
Constructs an equality constraint from a left and right side.
Definition variable.hpp:814
EqualityConstraints(std::initializer_list< EqualityConstraints > equality_constraints)
Concatenates multiple equality constraints.
Definition variable.hpp:781
gch::small_vector< Variable< Scalar > > constraints
A vector of scalar equality constraints.
Definition variable.hpp:775
EqualityConstraints(const std::vector< EqualityConstraints > &equality_constraints)
Concatenates multiple equality constraints.
Definition variable.hpp:795
A vector of inequality constraints of the form cᵢ(x) ≥ 0.
Definition variable.hpp:830
gch::small_vector< Variable< Scalar > > constraints
A vector of scalar inequality constraints.
Definition variable.hpp:832
InequalityConstraints(LHS &&lhs, RHS &&rhs)
Constructs an inequality constraint from a left and right side.
Definition variable.hpp:872
InequalityConstraints(const std::vector< InequalityConstraints > &inequality_constraints)
Concatenates multiple inequality constraints.
Definition variable.hpp:852
InequalityConstraints(std::initializer_list< InequalityConstraints > inequality_constraints)
Concatenates multiple inequality constraints.
Definition variable.hpp:838