Asymmetric Greedy Search
A Python implementation of the Asymmetric Greedy Search (AGS) algorithm, a fast heuristic for solving the Linear Sum Assignment Problem, based on the work of Brown et al. (2017).
Features
This package provides an efficient alternative to exact methods like the Hungarian algorithm, particularly for large, rectangular (asymmetric) matrices where exact solutions may be computationally expensive. It includes both NumPy and Numba backends and extends the original algorithm with features such as:
- Optional randomized greedy initialization
- Support for both cost minimization and benefit maximization
- Optional batched row updates between global swap benefit recalculations
Installation
pip install git+https://github.com/kaboroevich/asymmetric-greedy-search.git
Usage Example
from asymmetric_greedy_search import AsymmetricGreedySearch
import numpy as np
# Create a random benefit matrix (maximize benefit)
np.random.seed(57)
benefit = np.random.rand(100, 120)
ags = AsymmetricGreedySearch(backend='numba')
row_ind, assignment = ags.optimize(benefit)
score = benefit[row_ind, assignment].sum()
print(f"Total benefit: {score}")
Parameters
AsymmetricGreedySearch(backend = "numpy")
- backend (
str, optional): Specifies the computational backend to use for the algorithm.
Options are:"numpy"(default): Uses a NumPy-based implementation, suitable for general use."numba": Uses a Numba-accelerated implementation for improved performance on large problems.
AsymmetricGreedySearch.optimize(benefit, minimize=False, shuffle=False, maximum_iterations=0, stagnation_limit=0, stagnation_tolerance=1e-3, row_batch_size=1)
Runs the Asymmetric Greedy Search optimization on the provided benefit matrix.
- benefit (
numpy.ndarray): A 2D array representing the benefit or cost matrix for row-column assignments. - minimize (
bool): IfTrue, the algorithm minimizes the assignment costs instead of maximizing the benefit. Defaults toFalse. - shuffle (
bool): IfTrue, rows are shuffled before the greedy initialization to potentially improve solution diversity. Defaults toFalse. - maximum_iterations (
int): The maximum number of optimization iterations to perform. If set to0, no limit is applied. Defaults to0. - stagnation_limit (
int): The number of consecutive iterations allowed where the maximum improvement remains below a specified tolerance before terminating early. A value of0disables stagnation detection. Defaults to0. - stagnation_tolerance (
float): The relative improvement threshold used to detect stagnation. Stagnation is triggered if the maximum benefit improvement stays belowinitial_max_delta * stagnation_toleranceforstagnation_limitconsecutive iterations. Defaults to1e-3. - row_batch_size (
int): The number of rows to swap in each iteration, allowing batched updates to improve efficiency. Defaults to1(no batching).
Returns:
A tuple containing two NumPy arrays:
- The first array contains row indices.
- The second array contains the assigned column indices corresponding to each row.
Benchmarking
The examples/lsa_benchmark.ipynb notebook benchmarks AGS against SciPy's linear_sum_assignment, comparing runtime and assignment quality on synthetic distance matrices of increasing size.
AGS achieves solutions within a few percent of optimal (LSA) while offering orders-of-magnitude faster runtime on certain large matrices.
References
Brown, Peter, Yuedong Yang, Yaoqi Zhou, and Wayne Pullan. "A heuristic for the time constrained asymmetric linear sum assignment problem." Journal of Combinatorial Optimization 33 (2017): 551-566.
https://doi.org/10.1007/s10878-015-9979-2
Metadata
Release files for asymmetric-greedy-search 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| asymmetric_greedy_search-0.1.0.tar.gz | 47.0 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| asymmetric_greedy_search-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 83.2 kB
Release files / asymmetric_greedy_search-0.1.0.tar.gz
| Download URL | asymmetric_greedy_search-0.1.0.tar.gz |
|---|---|
| Size | 47.0 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
8bc0ce7588ba18825b25df3e6f684944b333fab3f5cf55ca9ff9c1e742511c1f
|
|
BLAKE2b-256 checksum How to use checksums |
23528e24a250235085069494970ff706001a1840aceefeed6836b2ef7a31583b
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.12.9
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jun 20, 2025.
Transparency logRelease files / asymmetric_greedy_search-0.1.0-py3-none-any.whl
| Download URL | asymmetric_greedy_search-0.1.0-py3-none-any.whl |
|---|---|
| Size | 36.2 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
80d3d18a58470feeec7822f3b754d58ec1dbda546fcb03cb7c5b48cffd948e58
|
|
BLAKE2b-256 checksum How to use checksums |
2213fd700ed38c832f47cf46c5f7e6a2b0fccf3307ef7cec7c41f5d14f9da728
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.12.9
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jun 20, 2025.
Transparency log