1 /* --------------------------------------------------------------------------
2 CppAD: C++ Algorithmic Differentiation: Copyright (C) 2003-20 Bradley M. Bell
3 
4 CppAD is distributed under the terms of the
5              Eclipse Public License Version 2.0.
6 
7 This Source Code may also be made available under the following
8 Secondary License when the conditions for such availability set forth
9 in the Eclipse Public License, Version 2.0 are satisfied:
10       GNU General Public License, Version 2.0 or later.
11 ---------------------------------------------------------------------------- */
12 
13 /*
14 $begin for_one.cpp$$
15 $spell
16     Cpp
17 $$
18 
19 
20 $section First Order Partial Driver: Example and Test$$
21 
22 $srcthisfile%0%// BEGIN C++%// END C++%1%$$
23 
24 $end
25 */
26 // BEGIN C++
27 # include <cppad/cppad.hpp>
28 namespace { // -------------------------------------------------------
29 // define the template function ForOneCases<Vector> in empty namespace
30 template <class Vector>
ForOneCases()31 bool ForOneCases()
32 {   bool ok = true;
33     using CppAD::AD;
34     using CppAD::NearEqual;
35     double eps99 = 99.0 * std::numeric_limits<double>::epsilon();
36     using CppAD::exp;
37     using CppAD::sin;
38     using CppAD::cos;
39 
40     // domain space vector
41     size_t n = 2;
42     CPPAD_TESTVECTOR(AD<double>)  X(n);
43     X[0] = 1.;
44     X[1] = 2.;
45 
46     // declare independent variables and starting recording
47     CppAD::Independent(X);
48 
49     // range space vector
50     size_t m = 3;
51     CPPAD_TESTVECTOR(AD<double>)  Y(m);
52     Y[0] = X[0] * exp( X[1] );
53     Y[1] = X[0] * sin( X[1] );
54     Y[2] = X[0] * cos( X[1] );
55 
56     // create f: X -> Y and stop tape recording
57     CppAD::ADFun<double> f(X, Y);
58 
59     // new value for the independent variable vector
60     Vector x(n);
61     x[0] = 2.;
62     x[1] = 1.;
63 
64     // compute partial of y w.r.t x[0]
65     Vector dy(m);
66     dy  = f.ForOne(x, 0);
67     ok &= NearEqual( dy[0], exp(x[1]), eps99, eps99); // for y[0]
68     ok &= NearEqual( dy[1], sin(x[1]), eps99, eps99); // for y[1]
69     ok &= NearEqual( dy[2], cos(x[1]), eps99, eps99); // for y[2]
70 
71     // compute partial of F w.r.t x[1]
72     dy  = f.ForOne(x, 1);
73     ok &= NearEqual( dy[0],  x[0]*exp(x[1]), eps99, eps99);
74     ok &= NearEqual( dy[1],  x[0]*cos(x[1]), eps99, eps99);
75     ok &= NearEqual( dy[2], -x[0]*sin(x[1]), eps99, eps99);
76 
77     return ok;
78 }
79 } // End empty namespace
80 # include <vector>
81 # include <valarray>
ForOne(void)82 bool ForOne(void)
83 {   bool ok = true;
84     // Run with Vector equal to three different cases
85     // all of which are Simple Vectors with elements of type double.
86     ok &= ForOneCases< CppAD::vector  <double> >();
87     ok &= ForOneCases< std::vector    <double> >();
88     ok &= ForOneCases< std::valarray  <double> >();
89     return ok;
90 }
91 // END C++
92