CppAD: A C++ Algorithmic Differentiation Package
20130102
|
00001 /* $Id$ */ 00002 # ifndef CPPAD_FUN_CHECK_INCLUDED 00003 # define CPPAD_FUN_CHECK_INCLUDED 00004 00005 /* -------------------------------------------------------------------------- 00006 CppAD: C++ Algorithmic Differentiation: Copyright (C) 2003-12 Bradley M. Bell 00007 00008 CppAD is distributed under multiple licenses. This distribution is under 00009 the terms of the 00010 Eclipse Public License Version 1.0. 00011 00012 A copy of this license is included in the COPYING file of this distribution. 00013 Please visit http://www.coin-or.org/CppAD/ for information on other licenses. 00014 -------------------------------------------------------------------------- */ 00015 00016 /* 00017 $begin FunCheck$$ 00018 $spell 00019 exp 00020 bool 00021 const 00022 Taylor 00023 $$ 00024 00025 $index FunCheck$$ 00026 $index check, ADFun$$ 00027 $index ADFun, check$$ 00028 00029 $section Check an ADFun Sequence of Operations$$ 00030 00031 $head Syntax$$ 00032 $icode%ok% = FunCheck(%f%, %g%, %x%, %r%, %a%)%$$ 00033 $pre 00034 $$ 00035 $bold See Also$$ 00036 $cref CompareChange$$ 00037 00038 00039 $head Purpose$$ 00040 We use $latex F : B^n \rightarrow B^m$$ to denote the 00041 $cref/AD function/glossary/AD Function/$$ corresponding to $icode f$$. 00042 We use $latex G : B^n \rightarrow B^m$$ to denote the 00043 function corresponding to the C++ function object $icode g$$. 00044 This routine check if 00045 $latex \[ 00046 F(x) = G(x) 00047 \]$$ 00048 If $latex F(x) \neq G(x)$$, the 00049 $cref/operation sequence/glossary/Operation/Sequence/$$ 00050 corresponding to $icode f$$ does not represents the algorithm used 00051 by $icode g$$ to calculate values for $latex G$$ 00052 (see $cref/Discussion/FunCheck/Discussion/$$ below). 00053 00054 $head f$$ 00055 The $code FunCheck$$ argument $icode f$$ has prototype 00056 $codei% 00057 ADFun<%Base%> %f% 00058 %$$ 00059 Note that the $cref ADFun$$ object $icode f$$ is not $code const$$ 00060 (see $cref/Forward/FunCheck/FunCheck Uses Forward/$$ below). 00061 00062 $head g$$ 00063 The $code FunCheck$$ argument $icode g$$ has prototype 00064 $codei% 00065 %Fun% &%g% 00066 %$$ 00067 ($icode Fun$$ is defined the properties of $icode g$$). 00068 The C++ function object $icode g$$ supports the syntax 00069 $codei% 00070 %y% = %g%(%x%) 00071 %$$ 00072 which computes $latex y = G(x)$$. 00073 00074 $subhead x$$ 00075 The $icode g$$ argument $icode x$$ has prototype 00076 $codei% 00077 const %Vector% &%x% 00078 %$$ 00079 (see $cref/Vector/FunCheck/Vector/$$ below) 00080 and its size 00081 must be equal to $icode n$$, the dimension of the 00082 $cref/domain/seq_property/Domain/$$ space for $icode f$$. 00083 00084 $head y$$ 00085 The $icode g$$ result $icode y$$ has prototype 00086 $codei% 00087 %Vector% %y% 00088 %$$ 00089 and its value is $latex G(x)$$. 00090 The size of $icode y$$ 00091 is equal to $icode m$$, the dimension of the 00092 $cref/range/seq_property/Range/$$ space for $icode f$$. 00093 00094 $head x$$ 00095 The $code FunCheck$$ argument $icode x$$ has prototype 00096 $codei% 00097 const %Vector% &%x% 00098 %$$ 00099 and its size 00100 must be equal to $icode n$$, the dimension of the 00101 $cref/domain/seq_property/Domain/$$ space for $icode f$$. 00102 This specifies that point at which to compare the values 00103 calculated by $icode f$$ and $icode G$$. 00104 00105 $head r$$ 00106 The $code FunCheck$$ argument $icode r$$ has prototype 00107 $codei% 00108 const %Base% &%r% 00109 %$$ 00110 It specifies the relative error the element by element 00111 comparison of the value of $latex F(x)$$ and $latex G(x)$$. 00112 00113 $head a$$ 00114 The $code FunCheck$$ argument $icode a$$ has prototype 00115 $codei% 00116 const %Base% &%a% 00117 %$$ 00118 It specifies the absolute error the element by element 00119 comparison of the value of $latex F(x)$$ and $latex G(x)$$. 00120 00121 $head ok$$ 00122 The $code FunCheck$$ result $icode ok$$ has prototype 00123 $codei% 00124 bool %ok% 00125 %$$ 00126 It is true, if for $latex i = 0 , \ldots , m-1$$ 00127 either the relative error bound is satisfied 00128 $latex \[ 00129 | F_i (x) - G_i (x) | 00130 \leq 00131 r ( | F_i (x) | + | G_i (x) | ) 00132 \] $$ 00133 or the absolute error bound is satisfied 00134 $latex \[ 00135 | F_i (x) - G_i (x) | \leq a 00136 \] $$ 00137 It is false if for some $latex (i, j)$$ neither 00138 of these bounds is satisfied. 00139 00140 $head Vector$$ 00141 The type $icode Vector$$ must be a $cref SimpleVector$$ class with 00142 $cref/elements of type/SimpleVector/Elements of Specified Type/$$ 00143 $icode Base$$. 00144 The routine $cref CheckSimpleVector$$ will generate an error message 00145 if this is not the case. 00146 00147 $head FunCheck Uses Forward$$ 00148 After each call to $cref Forward$$, 00149 the object $icode f$$ contains the corresponding 00150 $cref/Taylor coefficients/glossary/Taylor Coefficient/$$. 00151 After $code FunCheck$$, 00152 the previous calls to $cref Forward$$ are undefined. 00153 00154 $head Discussion$$ 00155 Suppose that the algorithm corresponding to $icode g$$ contains 00156 $codei% 00157 if( %x% >= 0 ) 00158 %y% = exp(%x%) 00159 else %y% = exp(-%x%) 00160 %$$ 00161 where $icode x$$ and $icode y$$ are $codei%AD<double>%$$ objects. 00162 It follows that the 00163 AD of $code double$$ $cref/operation sequence/glossary/Operation/Sequence/$$ 00164 depends on the value of $icode x$$. 00165 If the sequence of operations stored in $icode f$$ corresponds to 00166 $icode g$$ with $latex x \geq 0$$, 00167 the function values computed using $icode f$$ when $latex x < 0$$ 00168 will not agree with the function values computed by $latex g$$. 00169 This is because the operation sequence corresponding to $icode g$$ changed 00170 (and hence the object $icode f$$ does not represent the function 00171 $latex G$$ for this value of $icode x$$). 00172 In this case, you probably want to re-tape the calculations 00173 performed by $icode g$$ with the 00174 $cref/independent variables/glossary/Tape/Independent Variable/$$ 00175 equal to the values in $icode x$$ 00176 (so AD operation sequence properly represents the algorithm 00177 for this value of independent variables). 00178 00179 00180 $head Example$$ 00181 $children% 00182 example/fun_check.cpp 00183 %$$ 00184 The file 00185 $cref fun_check.cpp$$ 00186 contains an example and test of this function. 00187 It returns true if it succeeds and false otherwise. 00188 00189 $end 00190 --------------------------------------------------------------------------- 00191 */ 00192 00193 namespace CppAD { 00194 template <class Base, class Fun, class Vector> 00195 bool FunCheck( 00196 ADFun<Base> &f , 00197 Fun &g , 00198 const Vector &x , 00199 const Base &r , 00200 const Base &a ) 00201 { bool ok = true; 00202 00203 size_t m = f.Range(); 00204 Vector yf = f.Forward(0, x); 00205 Vector yg = g(x); 00206 00207 size_t i; 00208 for(i = 0; i < m; i++) 00209 ok &= NearEqual(yf[i], yg[i], r, a); 00210 return ok; 00211 } 00212 } 00213 00214 # endif