Cbc-Wrapper
This gem wraps the Coin-Or Cbc Mixed Integer Linear Programming Library. It uses the version 2.9.9 of Cbc.
Installation
This gem requires you to have Cbc installed on your system first.
- On a mac, you can execute
brew install cbc
- On Debian and Ubuntu, use
apt-get install coinor-libcbc-dev
- On Archlinux, use
pacman -S coin-or-cbc
Add this line to your application's Gemfile:
gem 'cbc-wrapper'
And then execute:
$ bundle
Or install it yourself as:
$ gem install cbc-wrapper
WARNING: if you want the gem to download and compile the library sources when installing the gem, you will need to use a lesser version of it (2.9.9.3).
Heroku
On Heroku, you will need to tweak your installation a bit: you can install the cbc library with the Apt buildpack with an Aptfile of:
coinor-libcbc-dev
You will need to set LD_LIBRARY_PATH so it can find LAPACK and BLAS (see this issue).
heroku config:set LD_LIBRARY_PATH=/app/.apt/usr/lib/x86_64-linux-gnu/lapack:/app/.apt/usr/lib/x86_64-linux-gnu/blas
Usage
All functions defined in Cbc_C_interface.h are wrapped. You can use any function named
func_name
with
Cbc_wrapper.func_name
You can find an example on how to use it at https://github.com/gverger/ruby-cbc.
Below is the Cbc_C_interface.h file:
/**@name Constructors and destructor
This is a "C" interface to Cbc.
The user does not need to know structure of Cbc_Model.
*/
/*@{*/
/** Default Cbc_Model constructor */
COINLIBAPI Cbc_Model * COINLINKAGE
Cbc_newModel(void)
;
/** Cbc_Model Destructor */
COINLIBAPI void COINLINKAGE
Cbc_deleteModel(Cbc_Model * model)
;
/** Current version of Cbc */
COINLIBAPI const char* COINLINKAGE Cbc_getVersion(void)
;
/*@}*/
/**@name Getting and setting model data
Note that problem access and modification methods,
such as getColLower and setColLower,
are *not valid* after calling Cbc_solve().
Therefore it is not recommended to reuse a Cbc_Model
object for multiple solves. A workaround is to call Cbc_clone()
before solving.
* */
/*@{*/
/** Loads a problem (the constraints on the
rows are given by lower and upper bounds). If a pointer is NULL then the
following values are the default:
<ul>
<li> <code>colub</code>: all columns have upper bound infinity
<li> <code>collb</code>: all columns have lower bound 0
<li> <code>rowub</code>: all rows have upper bound infinity
<li> <code>rowlb</code>: all rows have lower bound -infinity
<li> <code>obj</code>: all variables have 0 objective coefficient
</ul>
The constraint matrix is
given in standard compressed sparse column (without gaps).
<ul>
<li> <code>start[i]</code> stores the starting index of the ith column
<li> <code>index[k]</code> stores the row index of the kth nonzero element
<li> <code>value[k]</code> stores the coefficient of the kth nonzero element
</ul>
*/
COINLIBAPI void COINLINKAGE
Cbc_loadProblem (Cbc_Model * model, const int numcols, const int numrows,
const CoinBigIndex * start, const int* index,
const double* value,
const double* collb, const double* colub,
const double* obj,
const double* rowlb, const double* rowub)
;
/** Read an mps file from the given filename */
COINLIBAPI int COINLINKAGE
Cbc_readMps(Cbc_Model * model, const char *filename)
;
/** Write an mps file from the given filename */
COINLIBAPI void COINLINKAGE
Cbc_writeMps(Cbc_Model * model, const char *filename)
;
/** Provide an initial feasible solution to accelerate branch-and-bound
Note that feasibility of the solution is *not* verified.
*/
COINLIBAPI void COINLINKAGE
Cbc_setInitialSolution(Cbc_Model *model, const double * sol)
;
/** Fills in array with problem name */
COINLIBAPI void COINLINKAGE
Cbc_problemName(Cbc_Model * model, int maxNumberCharacters, char * array)
;
/** Sets problem name.
\p array must be a null-terminated string.
*/
COINLIBAPI int COINLINKAGE
Cbc_setProblemName(Cbc_Model * model, const char * array)
;
/** Number of nonzero elements in constraint matrix */
COINLIBAPI int COINLINKAGE
Cbc_getNumElements(Cbc_Model * model)
;
/** "Column start" vector of constraint matrix. Same format as Cbc_loadProblem() */
COINLIBAPI const CoinBigIndex * COINLINKAGE
Cbc_getVectorStarts(Cbc_Model * model)
;
/** "Row index" vector of constraint matrix */
COINLIBAPI const int * COINLINKAGE
Cbc_getIndices(Cbc_Model * model)
;
/** Coefficient vector of constraint matrix */
COINLIBAPI const double * COINLINKAGE
Cbc_getElements(Cbc_Model * model)
;
/** Maximum lenght of a row or column name */
COINLIBAPI size_t COINLINKAGE
Cbc_maxNameLength(Cbc_Model * model)
;
/** Fill in first maxLength bytes of name array with a row name */
COINLIBAPI void COINLINKAGE
Cbc_getRowName(Cbc_Model * model, int iRow, char * name, size_t maxLength)
;
/** Fill in first maxLength bytes of name array with a column name */
COINLIBAPI void COINLINKAGE
Cbc_getColName(Cbc_Model * model, int iColumn, char * name, size_t maxLength)
;
/** Set the name of a column */
COINLIBAPI void COINLINKAGE
Cbc_setColName(Cbc_Model * model, int iColumn, const char * name)
;
/** Set the name of a row */
COINLIBAPI void COINLINKAGE
Cbc_setRowName(Cbc_Model * model, int iRow, const char * name)
;
/** Number of constraints in the model */
COINLIBAPI int COINLINKAGE
Cbc_getNumRows(Cbc_Model * model)
;
/** Number of variables in the model */
COINLIBAPI int COINLINKAGE
Cbc_getNumCols(Cbc_Model * model)
;
/** Direction of optimization (1 - minimize, -1 - maximize, 0 - ignore) */
COINLIBAPI void COINLINKAGE
Cbc_setObjSense(Cbc_Model * model, double sense)
;
/** Direction of optimization (1 - minimize, -1 - maximize, 0 - ignore) */
COINLIBAPI double COINLINKAGE
Cbc_getObjSense(Cbc_Model * model)
;
/** Constraint lower bounds */
COINLIBAPI const double* COINLINKAGE
Cbc_getRowLower(Cbc_Model * model)
;
/** Set the lower bound of a single constraint */
COINLIBAPI void COINLINKAGE
Cbc_setRowLower(Cbc_Model * model, int index, double value)
;
/** Constraint upper bounds */
COINLIBAPI const double* COINLINKAGE
Cbc_getRowUpper(Cbc_Model * model)
;
/** Set the upper bound of a single constraint */
COINLIBAPI void COINLINKAGE
Cbc_setRowUpper(Cbc_Model * model, int index, double value)
;
/** Objective vector */
COINLIBAPI const double * COINLINKAGE
Cbc_getObjCoefficients(Cbc_Model * model)
;
/** Set the objective coefficient of a single variable */
COINLIBAPI void COINLINKAGE
Cbc_setObjCoeff(Cbc_Model * model, int index, double value)
;
/** Variable lower bounds */
COINLIBAPI const double * COINLINKAGE
Cbc_getColLower(Cbc_Model * model)
;
/** Set the lower bound of a single variable */
COINLIBAPI void COINLINKAGE
Cbc_setColLower(Cbc_Model * model, int index, double value)
;
/** Variable upper bounds */
COINLIBAPI const double * COINLINKAGE
Cbc_getColUpper(Cbc_Model * model)
;
/** Set the upper bound of a single variable */
COINLIBAPI void COINLINKAGE
Cbc_setColUpper(Cbc_Model * model, int index, double value)
;
/** Determine whether the ith variable is integer restricted */
COINLIBAPI int COINLINKAGE
Cbc_isInteger(Cbc_Model * model, int i)
;
/** Set this variable to be continuous */
COINLIBAPI void COINLINKAGE
Cbc_setContinuous(Cbc_Model * model, int iColumn)
;
/** Set this variable to be integer */
COINLIBAPI void COINLINKAGE
Cbc_setInteger(Cbc_Model * model, int iColumn)
;
/** Add SOS constraints to the model using row-order matrix */
COINLIBAPI void COINLINKAGE
Cbc_addSOS(Cbc_Model * model, int numRows, const int * rowStarts,
const int * colIndices, const double * weights, const int type)
;
/** Print the model */
COINLIBAPI void COINLINKAGE
Cbc_printModel(Cbc_Model * model, const char * argPrefix)
;
/** Return a copy of this model */
COINLIBAPI Cbc_Model * COINLINKAGE
Cbc_clone(Cbc_Model * model)
;
/*@}*/
/**@name Solver parameters */
/*@{*/
/** Set parameter "name" to value "value". Note that this
* translates directly to using "-name value" as a
* command-line argument to Cbc.*/
COINLIBAPI void COINLINKAGE
Cbc_setParameter(Cbc_Model * model, const char * name, const char * value)
;
/*@}*/
/**@name Message handling. Call backs are handled by ONE function */
/*@{*/
/** Pass in Callback function.
Message numbers up to 1000000 are Clp, Coin ones have 1000000 added */
COINLIBAPI void COINLINKAGE
Cbc_registerCallBack(Cbc_Model * model,
cbc_callback userCallBack)
;
/** Unset Callback function */
COINLIBAPI void COINLINKAGE
Cbc_clearCallBack(Cbc_Model * model)
;
/*@}*/
/**@name Solving the model */
/*@{*/
/* Solve the model with Cbc (using CbcMain1).
*/
COINLIBAPI int COINLINKAGE
Cbc_solve(Cbc_Model * model)
;
/*@}*/
/**@name Accessing the solution and solution status */
/*@{*/
/** Sum of primal infeasibilities */
COINLIBAPI double COINLINKAGE
Cbc_sumPrimalInfeasibilities(Cbc_Model * model)
;
/** Number of primal infeasibilities */
COINLIBAPI int COINLINKAGE
Cbc_numberPrimalInfeasibilities(Cbc_Model * model)
;
/** Just check solution (for external use) - sets sum of
infeasibilities etc */
COINLIBAPI void COINLINKAGE
Cbc_checkSolution(Cbc_Model * model)
;
/** Number of iterations */
COINLIBAPI int COINLINKAGE
Cbc_getIterationCount(Cbc_Model * model)
;
/** Are there a numerical difficulties? */
COINLIBAPI int COINLINKAGE
Cbc_isAbandoned(Cbc_Model * model)
;
/** Is optimality proven? */
COINLIBAPI int COINLINKAGE
Cbc_isProvenOptimal(Cbc_Model * model)
;
/** Is infeasiblity proven (or none better than cutoff)? */
COINLIBAPI int COINLINKAGE
Cbc_isProvenInfeasible(Cbc_Model * model)
;
/** Was continuous solution unbounded? */
COINLIBAPI int COINLINKAGE
Cbc_isContinuousUnbounded(Cbc_Model * model)
;
/** Node limit reached? */
COINLIBAPI int COINLINKAGE
Cbc_isNodeLimitReached(Cbc_Model * model)
;
/** Time limit reached? */
COINLIBAPI int COINLINKAGE
Cbc_isSecondsLimitReached(Cbc_Model * model)
;
/** Solution limit reached? */
COINLIBAPI int COINLINKAGE
Cbc_isSolutionLimitReached(Cbc_Model * model)
;
/** Are there numerical difficulties (for initialSolve) ? */
COINLIBAPI int COINLINKAGE
Cbc_isInitialSolveAbandoned(Cbc_Model * model)
;
/** Is optimality proven (for initialSolve) ? */
COINLIBAPI int COINLINKAGE
Cbc_isInitialSolveProvenOptimal(Cbc_Model * model)
;
/** Is primal infeasiblity proven (for initialSolve) ? */
COINLIBAPI int COINLINKAGE
Cbc_isInitialSolveProvenPrimalInfeasible(Cbc_Model * model)
;
/** "row" solution
* This is the vector A*x, where A is the constraint matrix
* and x is the current solution. */
COINLIBAPI const double * COINLINKAGE
Cbc_getRowActivity(Cbc_Model * model)
;
/** Best feasible solution vector */
COINLIBAPI const double * COINLINKAGE
Cbc_getColSolution(Cbc_Model * model)
;
/** Objective value of best feasible solution */
COINLIBAPI double COINLINKAGE
Cbc_getObjValue(Cbc_Model * model)
;
/** Best known bound on the optimal objective value */
COINLIBAPI double COINLINKAGE
Cbc_getBestPossibleObjValue(Cbc_Model * model)
;
/** Number of nodes explored in B&B tree */
COINLIBAPI int COINLINKAGE
Cbc_getNodeCount(Cbc_Model * model)
;
/** Print the solution */
COINLIBAPI void COINLINKAGE
Cbc_printSolution(Cbc_Model * model)
;
/** Final status of problem
Some of these can be found out by is...... functions
-1 before branchAndBound
0 finished - check isProvenOptimal or isProvenInfeasible to see if solution found
(or check value of best solution)
1 stopped - on maxnodes, maxsols, maxtime
2 difficulties so run was abandoned
(5 event user programmed event occurred)
*/
COINLIBAPI int COINLINKAGE
Cbc_status(Cbc_Model * model)
;
/** Secondary status of problem
-1 unset (status_ will also be -1)
0 search completed with solution
1 linear relaxation not feasible (or worse than cutoff)
2 stopped on gap
3 stopped on nodes
4 stopped on time
5 stopped on user event
6 stopped on solutions
7 linear relaxation unbounded
8 stopped on iteration limit
*/
COINLIBAPI int COINLINKAGE
Cbc_secondaryStatus(Cbc_Model * model)
;
Contributing
Bug reports and pull requests are welcome on GitHub at https://github.com/gverger/cbc-wrapper.