# Python-MIP: one modelling layer over CBC and Gurobi

> Python-MIP writes mixed-integer linear programs with operator overloading and hands them to CBC or Gurobi through CFFI, adding cut generation, lazy constraints, MIP starts and a solution pool on top of either solver.

**coin-or/python-mip** — Python-MIP: collection of Python tools for the modeling and solution of Mixed-Integer Linear programs

- Repository: https://github.com/coin-or/python-mip
- Stars: 605 · Forks: 108
- Language: Linear Programming
- License: EPL-2.0
- Published: 2026-10-22 · Updated: 2026-10-22 · Language: en
- Canonical page: https://hysenlabs.com/projects/coin-or-python-mip

## One solver independent API over CBC and Gurobi

Python-MIP is a collection of Python tools for modelling and solving mixed-integer linear programs, published to PyPI under the short name mip. Its defining feature is that it hides the differences between solvers. The project was written to be deeply integrated with the C libraries of the open-source COIN-OR branch and cut solver CBC and with the commercial solver Gurobi, and all of the details of talking to different solvers are handled inside the library so that you write solver independent code. That is the practical difference from a wrapper around a single vendor. If your model is prototyped on the free solver and then licensed for production, the model file does not change with the engine behind it. The project notes that the MIP syntax was inspired by Pulp, and that porting Pulp and Gurobi models should be quite easy, which makes this a reasonable migration target for teams arriving from either side.

## Models written as Python expressions, not a modelling DSL

The modelling layer is where most of the day to day work happens. The project describes high level modelling, writing MIP models in Python as easily as in high level languages such as MathProg, and says operator overloading makes it easy to write linear expressions in Python. In practice that means a constraint is written the way you would write arithmetic, with the overloaded operators assembling the linear expression and the model object deciding which row of the constraint matrix it belongs in. Compare that with a modelling language where you declare variables and push rows explicitly, and the difference in verbosity is large for models with many constraints. The cost is that the Python source no longer looks like a list of constraints, which matters for review and for debugging a model that behaves unexpectedly. The project also includes an example file named inplace_linexpr_creation.py, which suggests that building expressions in place is a supported and documented pattern rather than an accident of the implementation.

## Cut generators and lazy constraints inside the search

The advanced features are the reason to use a modelling layer rather than a plain solver library. Cut generators and lazy constraints let you work with strong formulations that have a large number of constraints by generating only the required inequalities during the branch and cut search. In plain terms, the constraints that are needed are produced while the search runs rather than all being handed to the solver up front, which keeps a hard formulation tractable. Lazy constraints serve the related purpose of rejecting a solution that satisfies the relaxation but breaks a property you only want to enforce on integral solutions, such as a subtour rule or a scheduling precedence that cannot be expressed linearly. The examples folder in the repository carries files with names that point at this style of model, including cutting_planes.py, cuttingstock_cg.py, cuttingstock_kantorovich.py, gen_cuts.py and gen_cuts_mip.py, along with combinatorial models such as knapsack.py, queens.py, jssp.py, rcpsp.py, plant_location.py and the travelling salesman files tsp-compact.py and tsp-compact-ulysses22.py.

## MIP starts and the solution pool

Two more solver capabilities are exposed directly. A MIP start lets you supply an initial feasible solution generated by a problem dependent heuristic, so the search can begin from a good point instead of from scratch, which matters when the default heuristic struggles with a particular structure. The solution pool lets you query the elite set of solutions found during the search, so a model can return several near-optimal alternatives rather than a single optimum, and your application can pick between them or show them to a user. The feature list alongside cut generation and lazy constraints marks this as full featured, and access to these advanced solver features is similar to what CyLP provides for the COIN-OR stack. For a project with a service level agreement about response time, a MIP start and a solution pool are usually worth more than a slightly better formulation, because they change how long the solver has to run.

## CFFI into the solver library, and the PyPy difference

The performance argument in the README is about the bridge, not about the solver. The package calls the native dynamic loadable library of the installed solver directly using the CFFI module, models are stored and optimised efficiently by the solver, and MIP handles all communication with your Python code. The Python implementation is typed and requires Python 3.8 or newer according to the project description. The headline claim is about PyPy: because the package is compatible with the PyPy just in time compiler, the project states you can have a much better performance, up to 25 times faster for the creation of large MIPs, than the official Gurobi python interface, which only runs on CPython. That is a model construction claim rather than a solve time claim, and it applies to building large models rather than to the branch and cut itself. The install requirements reflect the design, with cffi and cbcbox as the two required dependencies, since the CBC binary distribution is what makes the free solver usable without a separate installation step.

## The metadata floor and the README floor disagree

There is a discrepancy worth catching before you install. The project description says the library requires Python 3.8 or newer, while the project metadata in pyproject.toml declares requires-python of >=3.11 and the classifiers list Python 3.11 through 3.14, with both CPython and PyPy listed as supported implementations. The metadata is what the installer enforces, so on Python 3.8 to 3.10 the package will not install even though the README suggests it should. The same metadata file lists optional dependency groups that tell you what else you might need: a numpy extra pinned as >=1.25,<3, a gurobi extra with gurobipy >=10, a highs extra with highspy and highsbox where highsbox is limited to Windows platforms, and a test extra with pytest, networkx and matplotlib. The version is produced by setuptools-scm and written into mip/_version.py at build time, which is why the version field is dynamic rather than static in the file.

## Examples, benchmarks and where the licence stands

The examples library is substantial and is kept in the repository rather than only on the website. The examples directory holds more than twenty model scripts and data files, including the belgium-tourism-14.tsp and europe-tourism-22.tsp instance files used by the travelling salesman examples, plus apps and image directories, and a test.sh script for running them. A separate benchmarks directory sits at the top level, and a scripts directory, a test directory and a docs directory complete the layout. Documentation is published at docs.python-mip.com with a PDF version generated through readthedocs, and questions and feature requests go to the GitHub Discussions page. The licence is EPL-2.0, which the metadata records as the Eclipse Public License 2.0 and the classifier marks as an OSI approved licence, so the terms are weak copyleft and permissive in practice for most commercial use while still requiring that modifications to the library itself stay under the same terms. The release history shows v1.17.1 on 2026-03-02, a 1.16 pre-release on 2024-02-17 and v1.15.0 on 2023-01-04, and the last push was on 2026-09-25 with the repository not archived.

## Conclusion

Adopt Python-MIP if your team models in Python and wants one codebase that runs against CBC and Gurobi with the advanced solver features exposed. Do not pick it for a pure linear program where a solver library plus a modelling layer is enough, and check that your Python version matches the 3.11 floor in the project metadata before installing.

## FAQ

### Which solvers does Python-MIP support?

Python-MIP was written to integrate deeply with the C libraries of the open-source COIN-OR CBC solver and with the commercial Gurobi solver, and all solver communication is handled inside the library so your code stays solver independent. Optional dependency groups exist for gurobipy and for the HiGHS packages.

### How do I install Python-MIP?

The package is published on PyPI under the name mip, and the project points to the package website python-mip.com and the PyPI project page for downloads. The two required dependencies are cffi and cbcbox, the latter providing the CBC binary distribution.

### What Python version does Python-MIP need?

The project description says Python 3.8 or newer, but the project metadata declares requires-python >=3.11 and lists classifiers for Python 3.11 through 3.14. The metadata is what the installer enforces, so plan for 3.11 or newer.

### What are cut generation, lazy constraints and solution pools used for in Python-MIP?

Cut generators and lazy constraints let you work with strong formulations by generating only the required inequalities during the branch and cut search instead of passing every constraint up front. The solution pool lets you query the elite set of solutions found during the search rather than only the optimum.

### What licence is Python-MIP released under?

EPL-2.0, the Eclipse Public License 2.0, which the project metadata records as an OSI approved licence. It is weak copyleft, so commercial use is generally allowed while modifications to the library itself remain under the same terms.

## Sources

- [coin-or/python-mip on GitHub](https://github.com/coin-or/python-mip)
- [Issues](https://github.com/coin-or/python-mip/issues)
- [License: EPL-2.0](https://github.com/coin-or/python-mip/blob/master/LICENSE)
- [README](https://github.com/coin-or/python-mip/blob/master/README.md)
- [Releases](https://github.com/coin-or/python-mip/releases)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/coin-or-python-mip
