CppAD: A C++ Algorithmic Differentiation Package  20130918
mul_op.hpp
Go to the documentation of this file.
00001 /* $Id$ */
00002 # ifndef CPPAD_MUL_OP_INCLUDED
00003 # define CPPAD_MUL_OP_INCLUDED
00004 
00005 /* --------------------------------------------------------------------------
00006 CppAD: C++ Algorithmic Differentiation: Copyright (C) 2003-14 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 namespace CppAD { // BEGIN_CPPAD_NAMESPACE
00017 /*!
00018 \file mul_op.hpp
00019 Forward and reverse mode calculations for z = x * y.
00020 */
00021 
00022 // --------------------------- Mulvv -----------------------------------------
00023 /*!
00024 Compute forward mode Taylor coefficients for result of op = MulvvOp.
00025 
00026 The C++ source code corresponding to this operation is
00027 \verbatim
00028      z = x * y
00029 \endverbatim
00030 In the documentation below,
00031 this operations is for the case where both x and y are variables
00032 and the argument \a parameter is not used.
00033 
00034 \copydetails forward_binary_op
00035 */
00036 
00037 template <class Base>
00038 inline void forward_mulvv_op(
00039      size_t        p           , 
00040      size_t        q           , 
00041      size_t        i_z         ,
00042      const addr_t* arg         ,
00043      const Base*   parameter   ,
00044      size_t        nc_taylor   ,
00045      Base*         taylor      )
00046 {
00047      // check assumptions
00048      CPPAD_ASSERT_UNKNOWN( NumArg(MulvvOp) == 2 );
00049      CPPAD_ASSERT_UNKNOWN( NumRes(MulvvOp) == 1 );
00050      CPPAD_ASSERT_UNKNOWN( size_t(arg[0]) < i_z );
00051      CPPAD_ASSERT_UNKNOWN( size_t(arg[1]) < i_z );
00052      CPPAD_ASSERT_UNKNOWN( q < nc_taylor );
00053      CPPAD_ASSERT_UNKNOWN( p <= q );
00054 
00055      // Taylor coefficients corresponding to arguments and result
00056      Base* x = taylor + arg[0] * nc_taylor;
00057      Base* y = taylor + arg[1] * nc_taylor;
00058      Base* z = taylor + i_z    * nc_taylor;
00059 
00060      size_t k;
00061      for(size_t d = p; d <= q; d++)
00062      {    z[d] = Base(0);
00063           for(k = 0; k <= d; k++)
00064                z[d] += x[d-k] * y[k];
00065      }
00066 }
00067 
00068 /*!
00069 Compute zero order forward mode Taylor coefficients for result of op = MulvvOp.
00070 
00071 The C++ source code corresponding to this operation is
00072 \verbatim
00073      z = x * y
00074 \endverbatim
00075 In the documentation below,
00076 this operations is for the case where both x and y are variables
00077 and the argument \a parameter is not used.
00078 
00079 \copydetails forward_binary_op_0
00080 */
00081 
00082 template <class Base>
00083 inline void forward_mulvv_op_0(
00084      size_t        i_z         ,
00085      const addr_t* arg         ,
00086      const Base*   parameter   ,
00087      size_t        nc_taylor   ,
00088      Base*         taylor      )
00089 {
00090      // check assumptions
00091      CPPAD_ASSERT_UNKNOWN( NumArg(MulvvOp) == 2 );
00092      CPPAD_ASSERT_UNKNOWN( NumRes(MulvvOp) == 1 );
00093      CPPAD_ASSERT_UNKNOWN( size_t(arg[0]) < i_z );
00094      CPPAD_ASSERT_UNKNOWN( size_t(arg[1]) < i_z );
00095 
00096      // Taylor coefficients corresponding to arguments and result
00097      Base* x = taylor + arg[0] * nc_taylor;
00098      Base* y = taylor + arg[1] * nc_taylor;
00099      Base* z = taylor + i_z    * nc_taylor;
00100 
00101      z[0] = x[0] * y[0];
00102 }
00103 
00104 /*!
00105 Compute reverse mode partial derivatives for result of op = MulvvOp.
00106 
00107 The C++ source code corresponding to this operation is
00108 \verbatim
00109      z = x * y
00110 \endverbatim
00111 In the documentation below,
00112 this operations is for the case where both x and y are variables
00113 and the argument \a parameter is not used.
00114 
00115 \copydetails reverse_binary_op
00116 */
00117 
00118 template <class Base>
00119 inline void reverse_mulvv_op(
00120      size_t        d           , 
00121      size_t        i_z         ,
00122      const addr_t* arg         ,
00123      const Base*   parameter   ,
00124      size_t        nc_taylor   ,
00125      const Base*   taylor      ,
00126      size_t        nc_partial  ,
00127      Base*         partial     )
00128 {
00129      // check assumptions
00130      CPPAD_ASSERT_UNKNOWN( NumArg(MulvvOp) == 2 );
00131      CPPAD_ASSERT_UNKNOWN( NumRes(MulvvOp) == 1 );
00132      CPPAD_ASSERT_UNKNOWN( size_t(arg[0]) < i_z );
00133      CPPAD_ASSERT_UNKNOWN( size_t(arg[1]) < i_z );
00134      CPPAD_ASSERT_UNKNOWN( d < nc_taylor );
00135      CPPAD_ASSERT_UNKNOWN( d < nc_partial );
00136 
00137      // Arguments
00138      const Base* x  = taylor + arg[0] * nc_taylor;
00139      const Base* y  = taylor + arg[1] * nc_taylor;
00140 
00141      // Partial derivatives corresponding to arguments and result
00142      Base* px = partial + arg[0] * nc_partial;
00143      Base* py = partial + arg[1] * nc_partial;
00144      Base* pz = partial + i_z    * nc_partial;
00145 
00146 
00147      // number of indices to access
00148      size_t j = d + 1;
00149      size_t k;
00150      while(j)
00151      {    --j;
00152           for(k = 0; k <= j; k++)
00153           {    
00154                px[j-k] += pz[j] * y[k];
00155                py[k]   += pz[j] * x[j-k];
00156           }
00157      }
00158 }
00159 // --------------------------- Mulpv -----------------------------------------
00160 /*!
00161 Compute forward mode Taylor coefficients for result of op = MulpvOp.
00162 
00163 The C++ source code corresponding to this operation is
00164 \verbatim
00165      z = x * y
00166 \endverbatim
00167 In the documentation below,
00168 this operations is for the case where x is a parameter and y is a variable.
00169 
00170 \copydetails forward_binary_op
00171 */
00172 
00173 template <class Base>
00174 inline void forward_mulpv_op(
00175      size_t        p           , 
00176      size_t        q           , 
00177      size_t        i_z         ,
00178      const addr_t* arg         ,
00179      const Base*   parameter   ,
00180      size_t        nc_taylor   ,
00181      Base*         taylor      )
00182 {
00183      // check assumptions
00184      CPPAD_ASSERT_UNKNOWN( NumArg(MulpvOp) == 2 );
00185      CPPAD_ASSERT_UNKNOWN( NumRes(MulpvOp) == 1 );
00186      CPPAD_ASSERT_UNKNOWN( size_t(arg[1]) < i_z );
00187      CPPAD_ASSERT_UNKNOWN( q < nc_taylor );
00188      CPPAD_ASSERT_UNKNOWN( p <= q );
00189 
00190      // Taylor coefficients corresponding to arguments and result
00191      Base* y = taylor + arg[1] * nc_taylor;
00192      Base* z = taylor + i_z    * nc_taylor;
00193 
00194      // Paraemter value
00195      Base x = parameter[ arg[0] ];
00196 
00197      for(size_t d = p; d <= q; d++)
00198           z[d] = x * y[d];
00199 }
00200 /*!
00201 Compute zero order forward mode Taylor coefficient for result of op = MulpvOp.
00202 
00203 The C++ source code corresponding to this operation is
00204 \verbatim
00205      z = x * y
00206 \endverbatim
00207 In the documentation below,
00208 this operations is for the case where x is a parameter and y is a variable.
00209 
00210 \copydetails forward_binary_op_0
00211 */
00212 
00213 template <class Base>
00214 inline void forward_mulpv_op_0(
00215      size_t        i_z         ,
00216      const addr_t* arg         ,
00217      const Base*   parameter   ,
00218      size_t        nc_taylor   ,
00219      Base*         taylor      )
00220 {
00221      // check assumptions
00222      CPPAD_ASSERT_UNKNOWN( NumArg(MulpvOp) == 2 );
00223      CPPAD_ASSERT_UNKNOWN( NumRes(MulpvOp) == 1 );
00224      CPPAD_ASSERT_UNKNOWN( size_t(arg[1]) < i_z );
00225 
00226      // Paraemter value
00227      Base x = parameter[ arg[0] ];
00228 
00229      // Taylor coefficients corresponding to arguments and result
00230      Base* y = taylor + arg[1] * nc_taylor;
00231      Base* z = taylor + i_z    * nc_taylor;
00232 
00233      z[0] = x * y[0];
00234 }
00235 
00236 /*!
00237 Compute reverse mode partial derivative for result of op = MulpvOp.
00238 
00239 The C++ source code corresponding to this operation is
00240 \verbatim
00241      z = x * y
00242 \endverbatim
00243 In the documentation below,
00244 this operations is for the case where x is a parameter and y is a variable.
00245 
00246 \copydetails reverse_binary_op
00247 */
00248 
00249 template <class Base>
00250 inline void reverse_mulpv_op(
00251      size_t        d           , 
00252      size_t        i_z         ,
00253      const addr_t* arg         ,
00254      const Base*   parameter   ,
00255      size_t        nc_taylor   ,
00256      const Base*   taylor      ,
00257      size_t        nc_partial  ,
00258      Base*         partial     )
00259 {
00260      // check assumptions
00261      CPPAD_ASSERT_UNKNOWN( NumArg(MulvvOp) == 2 );
00262      CPPAD_ASSERT_UNKNOWN( NumRes(MulvvOp) == 1 );
00263      CPPAD_ASSERT_UNKNOWN( size_t(arg[1]) < i_z );
00264      CPPAD_ASSERT_UNKNOWN( d < nc_taylor );
00265      CPPAD_ASSERT_UNKNOWN( d < nc_partial );
00266 
00267      // Arguments
00268      Base x  = parameter[ arg[0] ];
00269 
00270      // Partial derivatives corresponding to arguments and result
00271      Base* py = partial + arg[1] * nc_partial;
00272      Base* pz = partial + i_z    * nc_partial;
00273 
00274      // number of indices to access
00275      size_t j = d + 1;
00276      while(j)
00277      {    --j;
00278           py[j] += pz[j] * x;
00279      }
00280 }
00281 
00282 
00283 } // END_CPPAD_NAMESPACE
00284 # endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines