Skip to main content

High-performance batched linear programming solver using HiGHS with parallel execution

Project description

batch-lp

PyPI version License: MIT

A high-performance batched linear programming solver using the HiGHS solver with parallel execution capabilities. Built with Rust and optimized for solving multiple LP problems simultaneously.

Features

  • ⚡ Fast Parallel Solving: Solve multiple LP problems simultaneously using Rayon's work-stealing parallelism
  • 🎯 Standard LP Form: Supports inequality constraints, equality constraints, and variable bounds
  • 🐍 Python Bindings: Easy-to-use Python interface with NumPy arrays via PyO3
  • 🚀 High Performance: Built on the HiGHS solver, one of the fastest open-source LP solvers
  • 🔧 Thread Control: Optionally specify the number of threads for parallel solving

Installation

From PyPI (recommended)

pip install batch-lp

From source

pip install maturin
git clone https://github.com/landonclark97/batch-lp.git
cd batch-lp
maturin develop --release

Quick Start

Solve a Single LP

import numpy as np
from batch_lp import solve_lp, Problem

# Problem: min -x - y
#          s.t. x + y <= 2
#               x, y >= 0

c = np.array([-1.0, -1.0])
A = np.array([[1.0, 1.0]])
b = np.array([2.0])

problem = Problem(c=c, A=A, b=b)
solution = solve_lp(problem)

print(f"Status: {solution.status}")
print(f"Objective: {solution.objective}")
print(f"Solution: {solution.x}")

Solve Multiple LPs in Parallel

import numpy as np
from batch_lp import solve_batch_lp, Problem

# Create 100 LP problems using the Problem class
problems = []
for i in range(100):
    problems.append(Problem(
        c=np.array([1.0, -1.0]),
        A=np.array([[1.0, 1.0], [1.0, -1.0]]),
        b=np.array([float(i + 2), 1.0]),
    ))

# Solve all problems in parallel (uses all CPU cores by default)
solutions = solve_batch_lp(problems)

for i, sol in enumerate(solutions[:5]):
    print(f"Problem {i}: {sol.status}, obj={sol.objective}")

Control Number of Threads

# Use 4 threads
solutions = solve_batch_lp(problems, num_threads=4)

# Use single thread (sequential)
solutions = solve_batch_lp(problems, num_threads=1)

# Use all available cores (default)
solutions = solve_batch_lp(problems)

Standard Form

The solver accepts problems in the form:

minimize    c^T x
subject to  A x <= b          (inequality constraints)
            A_eq x == b_eq    (equality constraints)
            lb <= x <= ub     (variable bounds)

Problem Class

Both solve_lp() and solve_batch_lp() use the Problem class to define LP problems:

from batch_lp import Problem
import numpy as np

problem = Problem(
    c=np.array([1.0, 2.0]),           # Objective coefficients (required)
    A=np.array([[1.0, 1.0]]),         # Inequality constraint matrix (optional)
    b=np.array([5.0]),                # Inequality RHS (optional)
    A_eq=np.array([[1.0, -1.0]]),     # Equality constraint matrix (optional)
    b_eq=np.array([0.0]),             # Equality RHS (optional)
    bounds=(0, 10),                   # Variable bounds (optional, default: (0, None))
)

Parameters

Parameter Type Description Default
c ndarray Objective coefficients (n,) Required
A ndarray Inequality constraint matrix (m_ineq, n) None
b ndarray Inequality RHS (m_ineq,) None
A_eq ndarray Equality constraint matrix (m_eq, n) None
b_eq ndarray Equality RHS (m_eq,) None
bounds tuple Variable bounds as (lower, upper) (0, None)

Bounds

The bounds parameter is a tuple (lower, upper) where each element can be:

  • None — no bound (-inf for lower, +inf for upper)
  • scalar — broadcast to all variables
  • ndarray — per-variable bounds
# Default: non-negative variables (0 <= x <= inf)
Problem(c=c, A=A, b=b)

# Scalar bounds broadcast to all variables
Problem(c=c, bounds=(0, 10))

# Completely unbounded variables
Problem(c=c, bounds=(None, None))

# Per-variable bounds
Problem(c=c, bounds=(np.array([0, -1, 0]), np.array([10, 5, 20])))

# Mix scalar and per-variable
Problem(c=c, bounds=(0, np.array([10, 5, 20])))

Examples

See example.py for comprehensive examples including:

  • Single LP solving
  • Equality constraints
  • Variable bounds
  • Batch solving
  • Thread control
  • Portfolio optimization

Run the example:

python example.py

How It Works

batch-lp leverages Rust's zero-cost abstractions and Rayon's work-stealing parallelism to efficiently solve multiple LP problems:

  1. No GIL: Python's Global Interpreter Lock is released during solving, enabling true parallelism
  2. Work Stealing: Rayon automatically balances load across threads
  3. No Overhead: Direct Rust ↔ HiGHS communication without Python overhead
  4. Shared Memory: No data pickling or IPC overhead like multiprocessing

Development

Building

# Development build
maturin develop

# Release build (optimized)
maturin develop --release

# Build wheel
maturin build --release

Testing

# Run Rust tests
cargo test

# Run Python example
python example.py

License

MIT License - see LICENSE file for details.

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

Acknowledgments

  • Built on top of the excellent HiGHS solver
  • Uses Rayon for parallelism
  • Python bindings via PyO3

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

batch_lp-1.0.3.tar.gz (18.7 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

batch_lp-1.0.3-cp39-abi3-win_amd64.whl (1.6 MB view details)

Uploaded CPython 3.9+Windows x86-64

batch_lp-1.0.3-cp39-abi3-manylinux_2_38_x86_64.whl (2.2 MB view details)

Uploaded CPython 3.9+manylinux: glibc 2.38+ x86-64

batch_lp-1.0.3-cp39-abi3-macosx_11_0_arm64.whl (1.7 MB view details)

Uploaded CPython 3.9+macOS 11.0+ ARM64

File details

Details for the file batch_lp-1.0.3.tar.gz.

File metadata

  • Download URL: batch_lp-1.0.3.tar.gz
  • Upload date:
  • Size: 18.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for batch_lp-1.0.3.tar.gz
Algorithm Hash digest
SHA256 14b2634474875d0c648e279c42f82a2f1455a9b5d2ff9aa1a80a07427b31acc6
MD5 4a8bdd1c0d09eef356f734b87de9624b
BLAKE2b-256 8a388149b39db92f1b85012175a184eea086a2153f7a2f75f384e150a53ec46e

See more details on using hashes here.

Provenance

The following attestation bundles were made for batch_lp-1.0.3.tar.gz:

Publisher: release.yml on landonclark97/batch-lp

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file batch_lp-1.0.3-cp39-abi3-win_amd64.whl.

File metadata

  • Download URL: batch_lp-1.0.3-cp39-abi3-win_amd64.whl
  • Upload date:
  • Size: 1.6 MB
  • Tags: CPython 3.9+, Windows x86-64
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for batch_lp-1.0.3-cp39-abi3-win_amd64.whl
Algorithm Hash digest
SHA256 f79bce97abc8e738a18f12e1b7d5aa50fc766492948f1bf1f41c939f3700b506
MD5 4fa3b789e9dce77e426cb28bd0693216
BLAKE2b-256 c0fa50899f73af66b5e5a98a09a0c4d3f4ace3965613c598b413bf509bc7ef62

See more details on using hashes here.

Provenance

The following attestation bundles were made for batch_lp-1.0.3-cp39-abi3-win_amd64.whl:

Publisher: release.yml on landonclark97/batch-lp

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file batch_lp-1.0.3-cp39-abi3-manylinux_2_38_x86_64.whl.

File metadata

File hashes

Hashes for batch_lp-1.0.3-cp39-abi3-manylinux_2_38_x86_64.whl
Algorithm Hash digest
SHA256 1cd918300e4340f34043f5d47a6ed7738eee7b5d4eb500f57c6642ae60b581c4
MD5 335805659ac420c481bcfd14a4ac7ce0
BLAKE2b-256 dba86e03f1bbae2efa94305da0b46ab5813f2e315a8ece2d29f033ddf3adf1a6

See more details on using hashes here.

Provenance

The following attestation bundles were made for batch_lp-1.0.3-cp39-abi3-manylinux_2_38_x86_64.whl:

Publisher: release.yml on landonclark97/batch-lp

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file batch_lp-1.0.3-cp39-abi3-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for batch_lp-1.0.3-cp39-abi3-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 00ed0521719db59cb8d0e3e410c526d35d7814fab015e07a52a77b599a412eae
MD5 526b2e9d61793cc77437b136f9dc8532
BLAKE2b-256 7c485ea0b0ff96bfd5021fb1f0425ad80f29bf3f5310d9375d42427f618b302e

See more details on using hashes here.

Provenance

The following attestation bundles were made for batch_lp-1.0.3-cp39-abi3-macosx_11_0_arm64.whl:

Publisher: release.yml on landonclark97/batch-lp

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page