diff --git a/include/boost/math/differentiation/autodiff_eigen.hpp b/include/boost/math/differentiation/autodiff_eigen.hpp index 1c7c44f977..6822da9fe0 100644 --- a/include/boost/math/differentiation/autodiff_eigen.hpp +++ b/include/boost/math/differentiation/autodiff_eigen.hpp @@ -20,40 +20,52 @@ struct NumTraits -struct ScalarBinaryOpTraits, - A, BinaryOp> { - typedef boost::math::differentiation::autodiff_v1::detail::template fvar< - RealType, Order> - ReturnType; -}; +// #define BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(A) \ +// template \ +// struct ScalarBinaryOpTraits, \ +// A, BinaryOp> { \ +// typedef boost::math::differentiation::autodiff_v1::detail::template fvar< \ +// Scalar, Order> \ +// ReturnType; \ +// }; \ +// template \ +// struct ScalarBinaryOpTraits, \ +// BinaryOp> { \ +// typedef boost::math::differentiation::autodiff_v1::detail::template fvar< \ +// Scalar, Order> \ +// ReturnType; \ +// }; -template -struct ScalarBinaryOpTraits, - BinaryOp> { - typedef boost::math::differentiation::autodiff_v1::detail::template fvar< - RealType, Order> - ReturnType; -}; +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(float); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(double); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(long double); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(short); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(unsigned short); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(int); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(unsigned int); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(long); +// BOOST_AUTODIFF_EIGEN_SCALAR_TRAITS(unsigned long); -template -struct ScalarBinaryOpTraits< - boost::math::differentiation::autodiff_v1::detail::template fvar, - boost::math::differentiation::autodiff_v1::detail::template fvar, - BinaryOp> { - typedef ScalarBinaryOpTraits::ReturnType - RealReturn; - const size_t ReturnOrder = (Order > Order2) ? Order : Order2; - typedef boost::math::differentiation::autodiff_v1::detail::template fvar< - RealReturn, ReturnOrder> - ReturnType; -} +// template +// struct ScalarBinaryOpTraits< +// boost::math::differentiation::autodiff_v1::detail::template +// fvar, +// boost::math::differentiation::autodiff_v1::detail::template +// fvar, +// BinaryOp> { +// typedef ScalarBinaryOpTraits::ReturnType +// RealReturn; +// const size_t ReturnOrder = (Order > Order2) ? Order : Order2; +// typedef boost::math::differentiation::autodiff_v1::detail::template fvar< +// RealReturn, ReturnOrder> +// ReturnType; +// }; } // namespace Eigen #endif // BOOST_MATH_DIFFERENTIATION_AUTODIFF_EIGEN_HPP diff --git a/test/test_autodiff_9.cpp b/test/test_autodiff_9.cpp index 926ef24449..9345f073cd 100644 --- a/test/test_autodiff_9.cpp +++ b/test/test_autodiff_9.cpp @@ -5,11 +5,13 @@ BOOST_AUTO_TEST_SUITE(test_autodiff_9) +using boost::math::differentiation::autodiff_v1::detail::fvar; + BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_init, T, all_float_types) { constexpr int size = 5; constexpr std::size_t n = 5; - typedef typename fvar fTn; + typedef fvar fTn; Eigen::Matrix x; x[0] = fTn(1.5); x[1] = make_fvar(2.5); @@ -18,7 +20,7 @@ BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_init, T, all_float_types) { x[4] = 5.5; constexpr std::size_t m = 2; - typedef typename fvar fTm; + typedef fvar fTm; Eigen::Matrix y; y = x.template cast(); BOOST_CHECK_EQUAL(x[0].derivative(0), y[0].derivative(0)); @@ -28,7 +30,7 @@ BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_init, T, all_float_types) { BOOST_CHECK_EQUAL(x[4].derivative(0), y[4].derivative(0)); constexpr std::size_t p = 3; - typedef typename fvar fTp; + typedef fvar fTp; Eigen::Matrix z = Eigen::Matrix::Random().transpose().template cast(); } @@ -44,12 +46,12 @@ BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_general, T, all_float_types) { constexpr std::size_t n = 2; constexpr double p = 3.456; - typedef typename fvar fTn; + typedef fvar fTn; Eigen::Matrix x; - x[0] = -1; - x[1] = 0; - x[2] = 1; - x[3] = 5; + x[0] = make_fvar(-1); + x[1] = make_fvar(0); + x[2] = make_fvar(1); + x[3] = make_fvar(5); Eigen::Matrix y1, y2, y3, y4, y5; y1 = sin(x); @@ -119,20 +121,20 @@ BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_general, T, all_float_types) { (p - 1) * p * pow(x[3].derivative(0), p - 2)); // Check log - BOOST_CHECK_EQUAL(y5[2].derivative(0), log(x[0].derivative(0)); - BOOST_CHECK_EQUAL(y5[3].derivative(0), log(x[3].derivative(0)); - BOOST_CHECK_EQUAL(y5[2].derivative(1), 1/x[2].derivative(0)); - BOOST_CHECK_EQUAL(y5[3].derivative(1), 1/x[3].derivative(0)); - BOOST_CHECK_EQUAL(y5[2].derivative(2), -1/pow(x[2].derivative(0), 2)); - BOOST_CHECK_EQUAL(y5[3].derivative(2), -1/pow(x[3].derivative(0), 2)); + BOOST_CHECK_EQUAL(y5[2].derivative(0), log(x[0].derivative(0))); + BOOST_CHECK_EQUAL(y5[3].derivative(0), log(x[3].derivative(0))); + BOOST_CHECK_EQUAL(y5[2].derivative(1), 1 / x[2].derivative(0)); + BOOST_CHECK_EQUAL(y5[3].derivative(1), 1 / x[3].derivative(0)); + BOOST_CHECK_EQUAL(y5[2].derivative(2), -1 / pow(x[2].derivative(0), 2)); + BOOST_CHECK_EQUAL(y5[3].derivative(2), -1 / pow(x[3].derivative(0), 2)); } BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_scalar, T, all_float_types) { constexpr int dim = 4; constexpr size_t n = 4; - typedef typename fvar fTn; - fTn x = 4; + typedef fvar fTn; + fTn x = make_fvar(4); Eigen::Matrix X; Eigen::Matrix Z; Eigen::Matrix I = Eigen::Matrix::Identity(); @@ -170,8 +172,8 @@ BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_vector, T, all_float_types) { constexpr int dim = 3; constexpr size_t n = 4; - typedef typename fvar fTn; - fTn x = 5; + typedef fvar fTn; + fTn x = make_fvar(5); T xD0 = x.derivative(0); Eigen::Matrix X; X[0] = 1; @@ -224,6 +226,32 @@ BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_vector, T, all_float_types) { xD0 * sin(xD0) - 4 * cos(xD0)); } -// BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_determinant, T, all_float_types) { -// constexpr int dim = 4; -// } +BOOST_AUTO_TEST_CASE_TEMPLATE(eigen_determinant, T, all_float_types) { + using std::cos; + using std::sin; + constexpr int dim = 4; + constexpr size_t n = 1; + + typedef fvar fTn; + fTn x = make_fvar(3); + T xD0 = x.derivative(0); + Eigen::Matrix M = 10 * Eigen::Matrix::Random(); + M(0, 3) = x; + M(1, 0) = 3 * x; + M(1, 2) = 1 / x; + M(2, 2) = x * x; + M(3, 1) = sin(x); + fTn y = M.determinant(); + + Eigen::Matrix dMdx = Eigen::Matrix::Zero(); + dMdx(0, 3) = 1; + dMdx(1, 0) = 3; + dMdx(1, 2) = -1 / (xD0 * xD0); + dMdx(2, 2) = 2 * xD0; + dMdx(3, 1) = cos(xD0); + + T ans = y.derivative(0) * (M.inverse() * dMdx).trace(); + BOOST_CHECK_EQUAL(y.derivative(1), ans); +} + +BOOST_AUTO_TEST_SUITE_END()