这是我发现的一个半官方示例:
- 函数定义(应该输出一个标量)
template <typename T>
T my_matrixfun(
Eigen::Matrix<T,Eigen::Dynamic,1> const &a,
Eigen::Matrix<T,Eigen::Dynamic,1> const &b)
{
Eigen::Matrix<T,Eigen::Dynamic,Eigen::Dynamic> m(a.size(),a.size());
m.setZero();
m.diagonal() = a;
return (b.transpose() * m * b)(0,0);
}
提取梯度和粗麻布:
typedef Eigen::Matrix<double,Eigen::Dynamic,1> inner_derivative_type;
typedef Eigen::AutoDiffScalar<inner_derivative_type> inner_active_scalar;
typedef Eigen::Matrix<inner_active_scalar,Eigen::Dynamic,1> outer_derivative_type;
typedef Eigen::AutoDiffScalar<outer_derivative_type> outer_active_scalar;
typedef Eigen::Matrix<outer_active_scalar,Eigen::Dynamic,1> AVector;
AVector Aa(a.size()),Ab(b.size());
// copy value from non-active example
for(int i=0;i<a.size();i++)Aa(i).value().value() = a(i);
for(int i=0;i<b.size();i++)Ab(i).value().value() = b(i);
// initialize derivative vectors
const int derivative_num = a.size() + b.size();
int derivative_idx = 0;
for(int i=0;i<Aa.size();i++){
init_twice_active_var(Aa(i),derivative_num,derivative_idx);
derivative_idx++;
}
for(int i=0;i<Ab.size();i++){
init_twice_active_var(Ab(i),derivative_num,derivative_idx);
derivative_idx++;
}
outer_active_scalar Ac = my_matrixfun(Aa,Ab);
std::cout << "Result: " << Ac.value().value() << std::endl;
std::cout << "Gradient: " <<
Ac.value().derivatives().transpose() << std::endl;
std::cout << "Hessian" << std::endl;
Eigen::MatrixXd hessian(Ac.derivatives().size(),Ac.derivatives().size());
for(int idx=0;idx<Ac.derivatives().size();idx++){
hessian.middleRows(idx,1) =
Ac.derivatives()(idx).derivatives().transpose();
}
std::cout << hessian << std::endl;