|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<html class="no-js" lang="en" >
|
|
Packit |
ea1746 |
<head>
|
|
Packit |
ea1746 |
<meta charset="utf-8">
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<title>Analytic Derivatives — Ceres Solver</title>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<link rel="top" title="Ceres Solver" href="index.html"/>
|
|
Packit |
ea1746 |
<link rel="up" title="On Derivatives" href="derivatives.html"/>
|
|
Packit |
ea1746 |
<link rel="next" title="Numeric derivatives" href="numerical_derivatives.html"/>
|
|
Packit |
ea1746 |
<link rel="prev" title="Spivak Notation" href="spivak_notation.html"/>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<script src="_static/js/modernizr.min.js"></script>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
</head>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<body class="wy-body-for-nav" role="document">
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<nav data-toggle="wy-nav-shift" class="wy-nav-side">
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Ceres Solver
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
1.13
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<form id="rtd-search-form" class="wy-form" action="search.html" method="get">
|
|
Packit |
ea1746 |
<input type="text" name="q" placeholder="Search docs" />
|
|
Packit |
ea1746 |
<input type="hidden" name="check_keywords" value="yes" />
|
|
Packit |
ea1746 |
<input type="hidden" name="area" value="default" />
|
|
Packit |
ea1746 |
</form>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Why?
|
|
Packit |
ea1746 |
Installation
|
|
Packit |
ea1746 |
Tutorial
|
|
Packit |
ea1746 |
On Derivatives
|
|
Packit |
ea1746 |
Spivak Notation
|
|
Packit |
ea1746 |
Analytic Derivatives
|
|
Packit |
ea1746 |
When should you use analytical derivatives?
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Numeric derivatives
|
|
Packit |
ea1746 |
Automatic Derivatives
|
|
Packit |
ea1746 |
Interfacing with Automatic Differentiation
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Modeling Non-linear Least Squares
|
|
Packit |
ea1746 |
Solving Non-linear Least Squares
|
|
Packit |
ea1746 |
Covariance Estimation
|
|
Packit |
ea1746 |
General Unconstrained Minimization
|
|
Packit |
ea1746 |
FAQS, Tips & Tricks
|
|
Packit |
ea1746 |
Users
|
|
Packit |
ea1746 |
Contributing
|
|
Packit |
ea1746 |
Version History
|
|
Packit |
ea1746 |
Bibliography
|
|
Packit |
ea1746 |
License
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
</nav>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<section data-toggle="wy-nav-shift" class="wy-nav-content-wrap">
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
<nav class="wy-nav-top" role="navigation" aria-label="top navigation">
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Ceres Solver
|
|
Packit |
ea1746 |
</nav>
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Docs »
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
On Derivatives »
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Analytic Derivatives
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
Analytic DerivativesΒΆ
|
|
Packit |
ea1746 |
Consider the problem of fitting the following curve (Rat43) to
|
|
Packit |
ea1746 |
data:
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
\[y = \frac{b_1}{(1+e^{b_2-b_3x})^{1/b_4}}\]
|
|
Packit |
ea1746 |
That is, given some data \(\{x_i, y_i\},\ \forall i=1,... ,n\),
|
|
Packit |
ea1746 |
determine parameters \(b_1, b_2, b_3\) and \(b_4\) that best
|
|
Packit |
ea1746 |
fit this data.
|
|
Packit |
ea1746 |
Which can be stated as the problem of finding the
|
|
Packit |
ea1746 |
values of \(b_1, b_2, b_3\) and \(b_4\) are the ones that
|
|
Packit |
ea1746 |
minimize the following objective function [1]:
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
\[\begin{split}\begin{align}
|
|
Packit |
ea1746 |
E(b_1, b_2, b_3, b_4)
|
|
Packit |
ea1746 |
&= \sum_i f^2(b_1, b_2, b_3, b_4 ; x_i, y_i)\\
|
|
Packit |
ea1746 |
&= \sum_i \left(\frac{b_1}{(1+e^{b_2-b_3x_i})^{1/b_4}} - y_i\right)^2\\
|
|
Packit |
ea1746 |
\end{align}\end{split}\]
|
|
Packit |
ea1746 |
To solve this problem using Ceres Solver, we need to define a
|
|
Packit |
ea1746 |
CostFunction that computes the residual \(f\) for a given
|
|
Packit |
ea1746 |
\(x\) and \(y\) and its derivatives with respect to
|
|
Packit |
ea1746 |
\(b_1, b_2, b_3\) and \(b_4\).
|
|
Packit |
ea1746 |
Using elementary differential calculus, we can see that:
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
\[\begin{split}\begin{align}
|
|
Packit |
ea1746 |
D_1 f(b_1, b_2, b_3, b_4; x,y) &= \frac{1}{(1+e^{b_2-b_3x})^{1/b_4}}\\
|
|
Packit |
ea1746 |
D_2 f(b_1, b_2, b_3, b_4; x,y) &=
|
|
Packit |
ea1746 |
\frac{-b_1e^{b_2-b_3x}}{b_4(1+e^{b_2-b_3x})^{1/b_4 + 1}} \\
|
|
Packit |
ea1746 |
D_3 f(b_1, b_2, b_3, b_4; x,y) &=
|
|
Packit |
ea1746 |
\frac{b_1xe^{b_2-b_3x}}{b_4(1+e^{b_2-b_3x})^{1/b_4 + 1}} \\
|
|
Packit |
ea1746 |
D_4 f(b_1, b_2, b_3, b_4; x,y) & = \frac{b_1 \log\left(1+e^{b_2-b_3x}\right) }{b_4^2(1+e^{b_2-b_3x})^{1/b_4}}
|
|
Packit |
ea1746 |
\end{align}\end{split}\]
|
|
Packit |
ea1746 |
With these derivatives in hand, we can now implement the
|
|
Packit |
ea1746 |
CostFunction as:
|
|
Packit |
ea1746 |
class Rat43Analytic : public SizedCostFunction<1,4> {
|
|
Packit |
ea1746 |
public:
|
|
Packit |
ea1746 |
Rat43Analytic(const double x, const double y) : x_(x), y_(y) {}
|
|
Packit |
ea1746 |
virtual ~Rat43Analytic() {}
|
|
Packit |
ea1746 |
virtual bool Evaluate(double const* const* parameters,
|
|
Packit |
ea1746 |
double* residuals,
|
|
Packit |
ea1746 |
double** jacobians) const {
|
|
Packit |
ea1746 |
const double b1 = parameters[0][0];
|
|
Packit |
ea1746 |
const double b2 = parameters[0][1];
|
|
Packit |
ea1746 |
const double b3 = parameters[0][2];
|
|
Packit |
ea1746 |
const double b4 = parameters[0][3];
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
residuals[0] = b1 * pow(1 + exp(b2 - b3 * x_), -1.0 / b4) - y_;
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
if (!jacobians) return true;
|
|
Packit |
ea1746 |
double* jacobian = jacobians[0];
|
|
Packit |
ea1746 |
if (!jacobian) return true;
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
jacobian[0] = pow(1 + exp(b2 - b3 * x_), -1.0 / b4);
|
|
Packit |
ea1746 |
jacobian[1] = -b1 * exp(b2 - b3 * x_) *
|
|
Packit |
ea1746 |
pow(1 + exp(b2 - b3 * x_), -1.0 / b4 - 1) / b4;
|
|
Packit |
ea1746 |
jacobian[2] = x_ * b1 * exp(b2 - b3 * x_) *
|
|
Packit |
ea1746 |
pow(1 + exp(b2 - b3 * x_), -1.0 / b4 - 1) / b4;
|
|
Packit |
ea1746 |
jacobian[3] = b1 * log(1 + exp(b2 - b3 * x_)) *
|
|
Packit |
ea1746 |
pow(1 + exp(b2 - b3 * x_), -1.0 / b4) / (b4 * b4);
|
|
Packit |
ea1746 |
return true;
|
|
Packit |
ea1746 |
}
|
|
Packit |
ea1746 |
|
|
Packit |
ea1746 |
private:
|
|
Packit |
ea1746 |
const double x_;
|
|
Packit |
ea1746 |
const double y_;
|
|
Packit |
ea1746 |
};
|