目录

1、IPOPT的安装(简洁版本)

2、IPOPT测试案例

3、ADOL-C的使用

4、CppAD的使用

 5、IPOPT的initial gauss 以及 warm star

参考链接:


优化,在Apollo规划模块中占据了重要的地位

Apollo中 OSQP 和 IPOPT 的应用:

OSQP

IPOPT

参考线:discrete_points_smoother(

FemPosSmooth

参考线:qp_spline_smoother

参考线:spiral_smoother

分段五次螺旋线非线性优化拟合

参考线:discrete_points_smoother(CosThetaSmooth

ipopt+adol-c

Lattice中横向规划中使用的基于二次规划的轨迹规划

Hybrid A*的轨迹优化

路径规划的QP

速度规划中DP之后的QP

速度规划中DP之后的IPOPT

其中OSQP在之前的文章中测试过,这篇文章主要进行IPOPT的相关实践

非线性优化的一般形式为:

非线性优化 python 非线性优化求解器_动态规划

IPOPT是一种常用的非线性优化求解器,使用内点法进行求解

对于复杂问题,需要借助自动微分工具,帮助求解梯度、Yacobian矩阵、Hessian矩阵,

如ADOL-C,CppAD

1、IPOPT的安装(简洁版本)

(1).安装apt包

sudo apt-get install gcc g++ gfortran git patch wget pkg-config liblapack-dev libmetis-dev

(2).安装BLAS and LAPACK

即为前面apt安装的liblapack-dev

(3).安装HSL 官网注册申请下载

需要教育网邮箱申请,

同时下载如下库.并将前面下载的HSL包解压后改名为coinhsl(例如coinhsl-archive-2021.05.05 => coinhsl)后复制到ThirdParty-HSL文件夹中,最后进行编译安装.

git clone https://github.com/coin-or-tools/ThirdParty-HSL.git
cd ThirdParty-HSL
./configure
make
sudo make install
sudo ldconfig

(4).安装IPOPT

mkdir build
cd build
sudo ../configure --prefix=/usr/local/ #安装到指定位置
sudo make
sudo make test
sudo make install

make test的输出应该如下:

Running unitTests...

Testing AMPL Solver Executable...
    Test passed!
Testing C++ Example...
    Test passed!
Testing C Example...
    Test passed!
Testing Fortran Example...
    Test passed!
Skip testing Java Example (Java interface not build)
Testing sIpopt Example parametric_cpp...
    Test passed!
Testing sIpopt Example redhess_cpp...
    Test passed!
Testing EmptyNLP Example...
    Test passed!
Testing GetCurr Example...
    Test passed!

(5).安装成功与否
进入IPOPT源码文件夹如下位置,用官方例子测试

cd Ipopt-releases-3.14.2/build/examples/Cpp_example
sudo make
./solver

2、IPOPT测试案例

#include "IpIpoptApplication.hpp"
#include "IpSolveStatistics.hpp"
#include "MyNLP.hpp"

#include <iostream>

using namespace Ipopt;

int main(int argv, char* argc[])
{
  // Create an instance of your nlp...
  SmartPtr<TNLP> mynlp = new MyNLP();

  // Create an instance of the IpoptApplication
  //
  // We are using the factory, since this allows us to compile this
  // example with an Ipopt Windows DLL
  SmartPtr<IpoptApplication> app = IpoptApplicationFactory();

  // Initialize the IpoptApplication and process the options
  ApplicationReturnStatus status;
  status = app->Initialize();
  if (status != Solve_Succeeded) {
    std::cout << std::endl << std::endl << "*** Error during initialization!" << std::endl;
    return (int) status;
  }

  status = app->OptimizeTNLP(mynlp);

  if (status == Solve_Succeeded) {
    // Retrieve some statistics about the solve
    Index iter_count = app->Statistics()->IterationCount();
    std::cout << std::endl << std::endl << "*** The problem solved in " << iter_count << " iterations!" << std::endl;

    Number final_obj = app->Statistics()->FinalObjective();
    std::cout << std::endl << std::endl << "*** The final value of the objective function is " << final_obj << '.' << std::endl;
  }

  return (int) status;
}

 

非线性优化 python 非线性优化求解器_sed_02

3、ADOL-C的使用

待补充

4、CppAD的使用

#include <iostream>
#include <cppad/ipopt/solve.hpp>

using namespace std;

namespace {
using CppAD::AD;
class FG_eval {
  public:
      typedef CPPAD_TESTVECTOR(AD<double>) ADvector;
      // 
      void operator()(ADvector& fg, const ADvector& x)
      {
          assert(fg.size() == 3);
          assert(x.size() == 4);
          // variables 优化变量
          AD<double> x1 = x[0];
          AD<double> x2 = x[1];
          AD<double> x3 = x[2];
          AD<double> x4 = x[3];
          // f(x) objective function 目标函数
          fg[0] = x1 * x4 * (x1 + x2 + x3) + x3;
          // constraints 约束条件
          fg[1] = x1 * x2 * x3 * x4;
          fg[2] = x1 * x1 + x2 * x2 + x3 * x3 + x4 * x4;
          return;
      }
  };
} //end namespace


bool get_started(void)
{
    bool ok = true;
    size_t i;
    typedef CPPAD_TESTVECTOR(double) Dvector;

    size_t nx = 4; // number of varibles 
    size_t ng = 2; // number of constraints 
    Dvector x0(nx); // initial condition of varibles 初始?

    x0[0] = 1.0;
    x0[1] = 5.0;
    x0[2] = 5.0;
    x0[3] = 1.0;

    // lower and upper bounds for varibles
    Dvector xl(nx), xu(nx);
    for(i = 0; i < nx; i++)
    {
        xl[i] = 1.0;
        xu[i] = 5.0;
    }
	
    //不等式上下界
    Dvector gl(ng), gu(ng);
    gl[0] = 25.0;    gu[0] = 1.0e19;
    gl[1] = 40.0;    gu[1] = 40.0;
    // object that computes objective and constraints
    FG_eval fg_eval;

    // options
    string options;
    // turn off any printing
    options += "Integer print_level  0\n";
    options += "String sb            yes\n";
    // maximum iterations
    options += "Integer max_iter     10\n";
    //approximate accuracy in first order necessary conditions;
    // see Mathematical Programming, Volume 106, Number 1,
    // Pages 25-57, Equation (6)
    options += "Numeric tol          1e-6\n";
    //derivative tesing
    options += "String derivative_test   second-order\n";
    // maximum amount of random pertubation; e.g.,
    // when evaluation finite diff
    options += "Numeric point_perturbation_radius   0.\n";

    //定义solution并求解
    CppAD::ipopt::solve_result<Dvector> solution; // solution
    CppAD::ipopt::solve<Dvector, FG_eval>(options, x0, xl, xu, gl, gu, fg_eval, solution); // solve the problem

    cout << "solution: " << solution.x << endl;

    //check some of the solution values 这个check有什么用?
    ok &= solution.status == CppAD::ipopt::solve_result<Dvector>::success;

    double check_x[]  = {1.000000, 4.743000, 3.82115, 1.379408};
    double check_zl[] = {1.087871, 0.,       0.,       0.      };
    double check_zu[] = {0.,       0.,       0.,       0.      };
    double rel_tol    = 1e-6; // relative tolerance
    double abs_tol    = 1e-6; // absolute tolerance
    for(i = 0; i < nx; i++)
    {
        ok &= CppAD::NearEqual(check_x[i], solution.x[i], rel_tol, abs_tol);
        ok &= CppAD::NearEqual(check_zl[i], solution.zl[i], rel_tol, abs_tol);
        ok &= CppAD::NearEqual(check_zu[i], solution.zu[i], rel_tol, abs_tol);
    }

    return ok;
}

int main()
{
    cout << "CppAD : Hello World Demo!" << endl;
    bool res = get_started();
    cout << "CppAD res:" << res << endl;
    return 0;
}

CMakeList.txt

project(ipopt_test)

cmake_minimum_required (VERSION 3.5)

add_definitions(-std=c++11 -O3)

add_executable(ipopt_test main.cpp)

target_link_libraries(ipopt_test ipopt)

 

非线性优化 python 非线性优化求解器_自动驾驶_03

 5、IPOPT的initial gauss 以及 warm star