17 #include <type_traits>
23 template <
class TScalar>
27 static auto numDiff(TFn curve, TScalar t, TScalar h) -> decltype(curve(t)) {
29 std::is_floating_point<TScalar>::value,
30 "Scalar must be a floating point type.");
32 return (curve(t + h) - curve(t - h)) / (TScalar(2) * h);
36 template <
class TScalar,
int kMatrixDim,
int kM>
40 std::function<Eigen::Vector<TScalar, kMatrixDim>(
41 Eigen::Vector<TScalar, kM>)> vector_field,
42 Eigen::Vector<TScalar, kM>
const& a,
43 TScalar eps) -> Eigen::Matrix<TScalar, kMatrixDim, kM> {
45 std::is_floating_point<TScalar>::value,
46 "Scalar must be a floating point type.");
47 Eigen::Matrix<TScalar, kMatrixDim, kM> j;
48 Eigen::Vector<TScalar, kM> h;
50 for (
int i = 0; i < kM; ++i) {
52 Eigen::Vector<TScalar, kMatrixDim> vfp = vector_field(a + h);
53 Eigen::Vector<TScalar, kMatrixDim> vfm = vector_field(a - h);
55 j.col(i) = (vfp - vfm) / (TScalar(2) * eps);
70 template <
class TScalar,
class TFn>
71 auto curveNumDiff(TFn curve, TScalar t, TScalar h = kEpsilonSqrt<TScalar>)
72 -> decltype(details::Curve<TScalar>::numDiff(std::move(curve), t, h)) {
73 return details::Curve<TScalar>::numDiff(std::move(curve), t, h);
85 class TScalarOrVector,
89 TScalarOrVector
const& a,
90 TScalar eps = kEpsilonSqrt<TScalar>)
91 -> Eigen::Matrix<TScalar, kMatrixDim, kM> {
92 return details::VectorField<TScalar, kMatrixDim, kM>::numDiff(
93 vector_field, a, eps);