deriv                 package:stats                 R Documentation

Symbolic and Algorithmic Derivatives of Simple Expressions

Description:

     Compute derivatives of simple expressions, symbolically.

Usage:

         D (expr, name)
      deriv(expr, ...)
     deriv3(expr, ...)

      ## Default S3 method:
      deriv(expr, namevec, function.arg = NULL, tag = ".expr",
            hessian = FALSE, ...)
      ## S3 method for class 'formula':
      deriv(expr, namevec, function.arg = NULL, tag = ".expr",
            hessian = FALSE, ...)

     ## Default S3 method:
     deriv3(expr, namevec, function.arg = NULL, tag = ".expr",
            hessian = TRUE, ...)
     ## S3 method for class 'formula':
     deriv3(expr, namevec, function.arg = NULL, tag = ".expr",
            hessian = TRUE, ...)

Arguments:

    expr: A 'expression' or 'call' or (except 'D') a formula with no
          lhs.

name,namevec: character vector, giving the variable names (only one for
          'D()') with respect to which derivatives will be computed.

function.arg: If specified and non-'NULL', a character vector of
          arguments for a function return, or a function (with empty
          body) or 'TRUE', the latter indicating that a function with
          argument names 'namevec' should be used.

     tag: character; the prefix to be used for the locally created
          variables in result.

 hessian: a logical value indicating whether the second derivatives
          should be calculated and incorporated in the return value.

     ...: arguments to tbe passed to or from methods.

Details:

     'D' is modelled after its S namesake for taking simple symbolic
     derivatives.

     'deriv' is a _generic_ function with a default and a 'formula'
     method.  It returns a 'call' for computing the 'expr' and its
     (partial) derivatives, simultaneously.  It uses so-called
     _algorithmic derivatives_.  If 'function.arg' is a function, its
     arguments can have default values, see the 'fx' example below.

     Currently, 'deriv.formula' just calls 'deriv.default' after
     extracting the expression to the right of '~'.

     'deriv3' and its methods are equivalent to 'deriv' and its methods
     except that 'hessian' defaults to 'TRUE' for 'deriv3'.

     The internal code knows about the arithmetic operators '+', '-',
     '*', '/' and '^', and the single-variable functions 'exp', 'log',
     'sin', 'cos', 'tan', 'sinh', 'cosh', 'sqrt', 'pnorm', 'dnorm',
     'asin', 'acos', 'atan', 'gamma' and 'lgamma'. (Note that only the
     standard normal distribution is considered.)

Value:

     'D' returns a call and therefore can easily be iterated for higher
     derivatives.

     'deriv' and 'deriv3' normally return an 'expression' object whose
     evaluation returns the function values with a '"gradient"'
     attribute containing the gradient matrix.  If 'hessian' is 'TRUE'
     the evaluation also returns a '"hessian"' attribute containing the
     Hessian array.

     If 'function.arg' is not 'NULL', 'deriv' and 'deriv3' return a
     function with those arguments rather than an expression.

References:

     Griewank, A.  and  Corliss, G. F. (1991) _Automatic
     Differentiation of Algorithms: Theory, Implementation, and
     Application_. SIAM proceedings, Philadelphia.

     Bates, D. M. and Chambers, J. M. (1992) _Nonlinear models._
     Chapter 10 of _Statistical Models in S_ eds J. M. Chambers and T.
     J. Hastie, Wadsworth & Brooks/Cole.

See Also:

     'nlm' and 'optim' for numeric minimization which could make use of
     derivatives,

Examples:

     ## formula argument :
     dx2x <- deriv(~ x^2, "x") ; dx2x
     ## Not run: 
     expression({
              .value <- x^2
              .grad <- array(0, c(length(.value), 1), list(NULL, c("x")))
              .grad[, "x"] <- 2 * x
              attr(.value, "gradient") <- .grad
              .value
     })
     ## End(Not run)
     mode(dx2x)
     x <- -1:2
     eval(dx2x)

     ## Something 'tougher':
     trig.exp <- expression(sin(cos(x + y^2)))
     ( D.sc <- D(trig.exp, "x") )
     all.equal(D(trig.exp[[1]], "x"), D.sc)

     ( dxy <- deriv(trig.exp, c("x", "y")) )
     y <- 1
     eval(dxy)
     eval(D.sc)

     ## function returned:
     deriv((y ~ sin(cos(x) * y)), c("x","y"), func = TRUE)

     ## function with defaulted arguments:
     (fx <- deriv(y ~ b0 + b1 * 2^(-x/th), c("b0", "b1", "th"),
                  function(b0, b1, th, x = 1:7){} ) )
     fx(2,3,4)

     ## Higher derivatives
     deriv3(y ~ b0 + b1 * 2^(-x/th), c("b0", "b1", "th"),
          c("b0", "b1", "th", "x") )

     ## Higher derivatives:
     DD <- function(expr,name, order = 1) {
        if(order < 1) stop("'order' must be >= 1")
        if(order == 1) D(expr,name)
        else DD(D(expr, name), name, order - 1)
     }
     DD(expression(sin(x^2)), "x", 3)
     ## showing the limits of the internal "simplify()" :
     ## Not run: 
     -sin(x^2) * (2 * x) * 2 + ((cos(x^2) * (2 * x) * (2 * x) + sin(x^2) *
         2) * (2 * x) + sin(x^2) * (2 * x) * 2)
     ## End(Not run)

