12b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// This file is part of Eigen, a lightweight C++ template library 22b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// for linear algebra. 32b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// 42b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// Copyright (C) 2013 Christoph Hertzberg <chtz@informatik.uni-bremen.de> 52b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// 62b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// This Source Code Form is subject to the terms of the Mozilla 72b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// Public License v. 2.0. If a copy of the MPL was not distributed 82b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang// with this file, You can obtain one at http://mozilla.org/MPL/2.0/. 92b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 102b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang#include "main.h" 112b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang#include <unsupported/Eigen/AutoDiff> 122b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 132b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang/* 142b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang * In this file scalar derivations are tested for correctness. 152b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang * TODO add more tests! 162b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang */ 172b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 182b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wangtemplate<typename Scalar> void check_atan2() 192b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang{ 202b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang typedef Matrix<Scalar, 1, 1> Deriv1; 212b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang typedef AutoDiffScalar<Deriv1> AD; 222b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 232b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD x(internal::random<Scalar>(-3.0, 3.0), Deriv1::UnitX()); 242b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 252b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang using std::exp; 262b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang Scalar r = exp(internal::random<Scalar>(-10, 10)); 272b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 282b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD s = sin(x), c = cos(x); 292b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD res = atan2(r*s, r*c); 302b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 312b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res.value(), x.value()); 322b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res.derivatives(), x.derivatives()); 332b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 342b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang res = atan2(r*s+0, r*c+0); 352b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res.value(), x.value()); 362b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res.derivatives(), x.derivatives()); 372b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang} 382b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 392b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wangtemplate<typename Scalar> void check_hyperbolic_functions() 402b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang{ 412b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang using std::sinh; 422b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang using std::cosh; 432b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang using std::tanh; 442b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang typedef Matrix<Scalar, 1, 1> Deriv1; 452b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang typedef AutoDiffScalar<Deriv1> AD; 462b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang Deriv1 p = Deriv1::Random(); 472b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD val(p.x(),Deriv1::UnitX()); 482b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 492b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang Scalar cosh_px = std::cosh(p.x()); 502b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD res1 = tanh(val); 512b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res1.value(), std::tanh(p.x())); 522b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res1.derivatives().x(), Scalar(1.0) / (cosh_px * cosh_px)); 532b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 542b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD res2 = sinh(val); 552b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res2.value(), std::sinh(p.x())); 562b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res2.derivatives().x(), cosh_px); 572b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 582b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang AD res3 = cosh(val); 592b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res3.value(), cosh_px); 602b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res3.derivatives().x(), std::sinh(p.x())); 612b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 622b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang // Check constant values. 632b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang const Scalar sample_point = Scalar(1) / Scalar(3); 642b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang val = AD(sample_point,Deriv1::UnitX()); 652b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang res1 = tanh(val); 662b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res1.derivatives().x(), Scalar(0.896629559604914)); 672b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 682b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang res2 = sinh(val); 692b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res2.derivatives().x(), Scalar(1.056071867829939)); 702b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 712b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang res3 = cosh(val); 722b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang VERIFY_IS_APPROX(res3.derivatives().x(), Scalar(0.339540557256150)); 732b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang} 742b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang 75eda03298de395cf6217486971e6529f92da8da79Miao Wangtemplate <typename Scalar> 76eda03298de395cf6217486971e6529f92da8da79Miao Wangvoid check_limits_specialization() 77eda03298de395cf6217486971e6529f92da8da79Miao Wang{ 78eda03298de395cf6217486971e6529f92da8da79Miao Wang typedef Eigen::Matrix<Scalar, 1, 1> Deriv; 79eda03298de395cf6217486971e6529f92da8da79Miao Wang typedef Eigen::AutoDiffScalar<Deriv> AD; 80eda03298de395cf6217486971e6529f92da8da79Miao Wang 81eda03298de395cf6217486971e6529f92da8da79Miao Wang typedef std::numeric_limits<AD> A; 82eda03298de395cf6217486971e6529f92da8da79Miao Wang typedef std::numeric_limits<Scalar> B; 83eda03298de395cf6217486971e6529f92da8da79Miao Wang 84eda03298de395cf6217486971e6529f92da8da79Miao Wang#if EIGEN_HAS_CXX11 85eda03298de395cf6217486971e6529f92da8da79Miao Wang VERIFY(bool(std::is_base_of<B, A>::value)); 86eda03298de395cf6217486971e6529f92da8da79Miao Wang#endif 87eda03298de395cf6217486971e6529f92da8da79Miao Wang} 88eda03298de395cf6217486971e6529f92da8da79Miao Wang 892b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wangvoid test_autodiff_scalar() 902b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang{ 912b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang for(int i = 0; i < g_repeat; i++) { 922b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang CALL_SUBTEST_1( check_atan2<float>() ); 932b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang CALL_SUBTEST_2( check_atan2<double>() ); 942b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang CALL_SUBTEST_3( check_hyperbolic_functions<float>() ); 952b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang CALL_SUBTEST_4( check_hyperbolic_functions<double>() ); 96eda03298de395cf6217486971e6529f92da8da79Miao Wang CALL_SUBTEST_5( check_limits_specialization<double>()); 972b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang } 982b8756b6f1de65d3f8bffab45be6c44ceb7411fcMiao Wang} 99