# SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later
# SPDX-FileCopyrightText: Bradley M. Bell <bradbell@seanet.com>
# SPDX-FileContributor: 2003-23 Bradley M. Bell
# ----------------------------------------------------------------------------
{xrst_begin forward_one}

First Order Forward Mode: Derivative Values
###########################################

Syntax
******
*y1* = *f* . ``Forward`` (1, *x1* )

Purpose
*******
We use :math:`F : \B{R}^n \rightarrow \B{R}^m` to denote the
:ref:`glossary@AD Function` corresponding to *f* .
The result of the syntax above is

.. math::

   y1 = F^{(1)} (x0) * x1

where :math:`F^{(1)} (x0)` is the Jacobian of :math:`F`
evaluated at *x0* .

f
*
The object *f* has prototype

   ``ADFun`` < *Base* > *f*

Note that the :ref:`ADFun-name` object *f* is not ``const`` .
Before this call to ``Forward`` , the value returned by

   *f* . ``size_order`` ()

must be greater than or equal one.
After this call it will be will be two (see :ref:`size_order-name` ).

x0
**
The vector *x0* in the formula

.. math::

   y1 = F^{(1)} (x0) * x1

corresponds to the previous call to :ref:`forward_zero-name`
using this ADFun object *f* ; i.e.,

   *f* . ``Forward`` (0, *x0* )

If there is no previous call with the first argument zero,
the value of the :ref:`Independent-name` variables
during the recording of the AD sequence of operations is used
for *x0* .

x1
**
The argument *x1* has prototype

   ``const`` *Vector* & *x1*

(see :ref:`forward_one@Vector` below)
and its size must be equal to *n* , the dimension of the
:ref:`fun_property@Domain` space for *f* .

Vector
******
The type *Vector* must be a :ref:`SimpleVector-name` class with
:ref:`elements of type<SimpleVector@Elements of Specified Type>`
*Base* .
The routine :ref:`CheckSimpleVector-name` will generate an error message
if this is not the case.

Example
*******
The file
:ref:`forward.cpp-name`
contains an example and test of this operation.

Special Case
************
This is special case of :ref:`forward_order-name` where

.. math::
   :nowrap:

   \begin{eqnarray}
   Y(t) & = & F[ X(t) ]
   \\
   X(t) & = & x^{(0)} t^0 + x^{(1)} * t^1 + \cdots, + x^{(q)} * t^q + o( t^q )
   \\
   Y(t) & = & y^{(0)} t^0 + y^{(1)} * t^1 + \cdots, + y^{(q)} * t^q + o( t^q )
   \end{eqnarray}

and :math:`o( t^q ) * t^{-q} \rightarrow 0` as :math:`t \rightarrow 0`.
For this special case, :math:`q = 1`,
:math:`x^{(0)}` = *x0* ,
:math:`x^{(1)}` = *x1* ,
:math:`X(t) = x^{(0)} + x^{(1)} t`, and

.. math::

   y^{(0)} + y^{(1)} t  = F [ x^{(0)} + x^{(1)} t ] + o(t)

Taking the derivative with respect to :math:`t`, at :math:`t = 0`,
we obtain

.. math::

   y^{(1)} = F^{(1)} [ x^{(0)} ] x^{(1)}

which agrees with the specifications for
*y1* in the :ref:`forward_one@Purpose` above.

{xrst_end forward_one}
