最近学习了一下OOQP的使用在这里记录一下。
在matlab代码中是quadprog,而这次使用OOQP也主要是为了计算二次规划问题。
安装OOQP
首先是安装问题,不得不说,当时安装也花了不少时间,如果是第一次,确实不是很好安装
github https://github.com/emgertz/OOQP
OOQP主页 http://pages.cs.wisc.edu/~swright/ooqp/
直接git clone下载文件源码 git clone https://github.com/emgertz/OOQP
英文版的安装说明 http://pages.cs.wisc.edu/~swright/ooqp/INSTALL.html
安装依赖BLAS和MA27(或MA57)
BLAS 直接按照其中的命令安装
https://www.jianshu.com/p/fe6c4f42aa0b
下载MA27我是直接在github上下载的,当然你也可以去官网上去下载 https://github.com/HITSZ-LeggedRobotics/ma27
MA57和MA27选择其中一个就可以
安装好依赖后,注意在编译源码的时候,把库文件的位置链接清楚,不然编译不会成功。
使用说明
官网给出了一分详细的使用说明
- User Manual: E. M. Gertz and S. J. Wright, OOQP User Guide, October, 2001. Updated May 2004.
但是英文如果不太行的,确实看着很吃力
这里我看到一维博主对其中c++的使用进行了比较详细的翻译 https://qiaoxu123.github.io/post/ubuntu-ooqp-useguide/
在给出约束的时候,很有意思,你需要按照他的方式,把约束的值,塞进数组里面,我在这里单独写了一个函数来做这个事情。以下给出的代码是官网文档中给出的示例题写的
Code details
/* OOQP *
* Authors: E. Michael Gertz, Stephen J. Wright *
* (C) 2001 University of Chicago. See Copyright Notification in OOQP */
#include "QpGenData.h"
#include "QpGenVars.h"
#include "QpGenResiduals.h"
#include "GondzioSolver.h"
#include "QpGenSparseMa27.h"
#include <iostream>
#include <string.h>
using namespace std;
const int nx = 2;
double c[] = { 1.5, -2 };
double xupp[] = { 20, 0 };
char ixupp[] = { 1, 0 };
double xlow[] = { 0, 0 };
char ixlow[] = { 1, 1 };
const int nnzQ = 3;
int irowQ[] = { 0, 1, 1 };
int jcolQ[] = { 0, 0, 1 };
double dQ[] = { 8, 2, 10 };
int my = 0;
double * b = 0;
int nnzA = 0;
int * irowA = 0;
int * jcolA = 0;
double * dA = 0;
const int mz = 2;
double clow[] = { 2, 0 };
char iclow[] = { 1, 0 };
double cupp[] = { 0, 6 };
char icupp[] = { 0, 1 };
const int nnzC = 4;
int irowC[] = { 0, 0, 1, 1};
int jcolC[] = { 0, 1, 0, 1};
double dC[] = { 2, 1, -1, 2};
int main( int argc, char * argv[] )
{
int usage_ok = 1, quiet = 0;
if( argc > 2 ) usage_ok = 0;
if( argc == 2 ) {
if( 0 == strcmp( "--quiet", argv[1] ) ) {
quiet = 1;
} else {
usage_ok = 0;
}
}
if( !usage_ok ) {
cerr << "Usage: " << argv[0] << " [ --quiet ]\n";
return 1;
}
QpGenSparseMa27 * qp
= new QpGenSparseMa27( nx, my, mz, nnzQ, nnzA, nnzC );
QpGenData * prob = (QpGenData * ) qp->copyDataFromSparseTriple(
c, irowQ, nnzQ, jcolQ, dQ,
xlow, ixlow, xupp, ixupp,
irowA, nnzA, jcolA, dA, b,
irowC, nnzC, jcolC, dC,
clow, iclow, cupp, icupp );
QpGenVars * vars
= (QpGenVars *) qp->makeVariables( prob );
QpGenResiduals * resid
= (QpGenResiduals *) qp->makeResiduals( prob );
GondzioSolver * s = new GondzioSolver( qp, prob );
if( !quiet ) s->monitorSelf();
int ierr = s->solve(prob,vars, resid);
if( ierr == 0 ) {
cout.precision(4);
cout << "Solution: \n";
vars->x->writefToStream( cout, "x[%{index}] = %{value}" );
} else {
cout << "Could not solve the problem.\n";
}
return ierr;
}
我的CMakeLists.txt
如果有兴趣你也可以看看源代码中examples里面的其它例子
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)