CppAD: A C++ Algorithmic Differentiation Package 20110419
abs.hpp
Go to the documentation of this file.
00001 /* $Id$ */
00002 # ifndef CPPAD_ABS_INCLUDED
00003 # define CPPAD_ABS_INCLUDED
00004 
00005 /* --------------------------------------------------------------------------
00006 CppAD: C++ Algorithmic Differentiation: Copyright (C) 2003-09 Bradley M. Bell
00007 
00008 CppAD is distributed under multiple licenses. This distribution is under
00009 the terms of the 
00010                     Common 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 -------------------------------------------------------------------------------
00018 $begin abs$$
00019 $spell
00020         Vec
00021         std
00022         faq
00023         Taylor
00024         Cpp
00025         namespace
00026         const
00027         abs
00028 $$
00029 
00030 $index abs, AD$$
00031 $index absolute, AD value$$
00032 $index value_, AD absolute$$
00033 
00034 $section AD Absolute Value Function$$
00035 
00036 $head Syntax$$
00037 $syntax%%y% = abs(%x%)%$$
00038 
00039 
00040 $head Purpose$$
00041 Evaluates the absolute value function.
00042 
00043 
00044 $head x$$
00045 The argument $italic x$$ has one of the following prototypes
00046 $syntax%
00047         const AD<%Base%>               &%x%
00048         const VecAD<%Base%>::reference &%x%
00049 %$$
00050 
00051 $head y$$
00052 The result $italic y$$ has prototype
00053 $syntax%
00054         AD<%Base%> %y%
00055 %$$
00056 
00057 
00058 $head Operation Sequence$$
00059 This is an AD of $italic Base$$
00060 $xref/glossary/Operation/Atomic/atomic operation/1/$$
00061 and hence is part of the current
00062 AD of $italic Base$$
00063 $xref/glossary/Operation/Sequence/operation sequence/1/$$.
00064 
00065 $head Complex Types$$
00066 The function $code abs$$ is not defined for the AD type sequences
00067 above $code std::complex<float>$$ or $code std::complex<double>$$
00068 because the complex $code abs$$ function is not complex differentiable
00069 (see $xref/Faq/Complex Types/complex types faq/$$).
00070 
00071 $head Directional Derivative$$
00072 $index directional, derivative abs$$
00073 $index derivative, directional abs$$
00074 The derivative of the absolute value function is one for 
00075 $latex x > 0$$ and minus one for $latex x < 0$$.
00076 The subtitle issue is 
00077 how to compute its directional derivative
00078 what $latex x = 0$$.
00079 $pre
00080 
00081 $$
00082 The function corresponding to the argument $italic x$$ 
00083 and the result $italic y$$ are represented
00084 by their Taylor coefficients; i.e.,
00085 $latex \[
00086 \begin{array}{rcl}
00087         X(t) & = & x^{(0)} (t) + x^{(1)} t + \cdots + x^{(p)} t^p
00088         \\
00089         Y(t) & = & y^{(0)} (t) + y^{(1)} t + \cdots + y^{(p)} t^p
00090 \end{array}
00091 \] $$
00092 Note that $latex x^{(0)} = X(0)$$ is the value of $italic x$$ and
00093 $latex y^{(0)} = Y(0)$$ is the value of $italic y$$.
00094 In the equations above, the order $latex p$$ is specified
00095 by a call to $xref/Forward/$$ or $xref/Reverse/$$ as follows:
00096 $syntax%
00097         %f%.Forward(%p%, %dx%)
00098         %f%.Reverse(%p%+1, %w%)
00099 %$$
00100 If all of the Taylor coefficients of $latex X(t)$$ are zero,
00101 we define $latex k = p$$.
00102 Otherwise, we define $latex k$$ to be the minimal index such that 
00103 $latex x^{(k)} \neq 0$$.
00104 Note that if $latex x \neq 0$$, $latex k = 0$$.
00105 The Taylor coefficient representation of $latex Y(t)$$
00106 (and hence it's derivatives) are computed as
00107 $latex \[
00108 y^{(\ell)}
00109 =
00110 \left\{ \begin{array}{ll} 
00111          x^{(\ell)}   & {\rm if} \; x^{(k)} > 0         \\
00112          0                    & {\rm if} \; x^{(k)} = 0 \\
00113         - x^{(\ell)}  & {\rm if} \; x^{(k)} < 0
00114 \end{array} \right.
00115 \] $$
00116 
00117 
00118 $head Example$$
00119 $children%
00120         example/abs.cpp
00121 %$$
00122 The file
00123 $xref/Abs.cpp/$$
00124 contains an example and test of this function.   
00125 It returns true if it succeeds and false otherwise.
00126 
00127 $end
00128 -------------------------------------------------------------------------------
00129 */
00130 
00131 //  BEGIN CppAD namespace
00132 namespace CppAD {
00133 
00134 template <class Base>
00135 AD<Base> AD<Base>::Abs (void) const
00136 { 
00137         AD<Base> result;
00138         result.value_ = abs(value_);
00139         CPPAD_ASSERT_UNKNOWN( Parameter(result) );
00140 
00141         if( Variable(*this) ) 
00142         {       // add this operation to the tape
00143                 CPPAD_ASSERT_UNKNOWN( NumRes(AbsOp) == 1 );
00144                 CPPAD_ASSERT_UNKNOWN( NumArg(AbsOp) == 1 );
00145                 ADTape<Base> *tape = tape_this();
00146 
00147                 // corresponding operand address
00148                 tape->Rec_.PutArg(taddr_);
00149                 // put operator in the tape
00150                 result.taddr_ = tape->Rec_.PutOp(AbsOp);
00151                 // make result a variable
00152                 result.id_    = tape->id_;
00153         }
00154         return result;
00155 }
00156 
00157 template <class Base>
00158 inline AD<Base> abs(const AD<Base> &x)
00159 {       return x.Abs(); }
00160 
00161 template <class Base>
00162 inline AD<Base> abs(const VecAD_reference<Base> &x)
00163 {       return abs( x.ADBase() ); }
00164 
00165 } // END CppAD namespace
00166 
00167 # endif