Proxima
A C++17 implementation of the Hierarchical Navigable Small World (HNSW) approximate nearest neighbor search algorithm.
Proxima is designed for learning, experimentation, and performance evaluation, with a readable from-scratch implementation, configurable parameters, multiple distance metrics, SIMD acceleration, and Python bindings.
Based on "Efficient and robust approximate nearest neighbor search using Hierarchical Navigable Small World graphs" by Yu. A. Malkov and D. A. Yashunin.
Features
- Multi-layer HNSW graph with exponentially decaying level distribution
- Heuristic neighbor selection from the HNSW paper
- Distance metrics:
- L2 / squared Euclidean
- Inner product
- Cosine similarity
- SIMD acceleration:
- AVX2 + FMA on x86_64
- NEON on ARM64
- Scalar fallback
- Python bindings using nanobind
- GoogleTest unit tests with
AddressSanitizerandUndefinedBehaviorSanitizer - C++ and Python benchmarks
- Comparison against brute-force search and hnswlib
clang-formatandclang-tidyintegration- Python packaging with
uv, scikit-build-core, CMake, and nanobind - Python 3.12+ with
abi3wheels
Prerequisites
C++
- CMake >= 3.18
- C++17 compiler
- clang-format
- clang-tidy
Python
- Python >= 3.12
- uv
Development dependencies are managed through uv.
Install development tools and dependencies:
make setup
make python
Development
The Makefile provides the main development interface:
$ make help
Proxima
Build:
make setup Install development tools
make configure Configure CMake
make build Build C++ project
make rebuild Clean rebuild
make clean Remove build directory
Tests:
make test Run C++ tests
make python-test Run Python tests
make python-all-test Run all Python tests
make ci Run full CI checks
Python:
make python Install Python package/dependencies
make package Build wheel + sdist
make wheel Build wheel only
make sdist Build source distribution
make package-check Validate distributions
make package-local Test wheel in clean local venv
make package-test Alias for package-local
Publishing:
make publish-test TOKEN=... Upload to TestPyPI
make publish TOKEN=... Upload to PyPI
Benchmarks:
make cppbench Run C++ benchmark
make pybindings-bench Run Python bindings benchmark
make pybench Run hnswlib benchmark
make bench Run complete benchmark suite
make compare Generate comparison
make plot Generate plots
Code Quality:
make format Format C++ code
make format-check Check formatting
make lint Run clang-tidy
make lint-fix Run clang-tidy with fixes
Release:
make release-check Run all release checks
Benchmark example:
make bench RUN_DIR=my-run
Build, test, format, lint, benchmark, and packaging workflows are all available through make.
Benchmarks
Run the complete benchmark suite:
make bench
This runs:
- C++ Proxima vs brute-force
- Python bindings vs brute-force
- Python hnswlib vs brute-force
- Comparison reports
- Plots
Results are stored under:
benchmarks/results/<run-directory>/
A custom run directory can be specified with:
make bench RUN_DIR=my-run
Python Package
# Build the source distribution
make package
# Validate the distributions
make package-check
# Test the actual built wheel in a clean temporary virtual environment (which is automatically removed after the test completes)
make package-test
TestPyPI
Test the complete publishing workflow before releasing to PyPI:
# This :
# 1. Builds the package.
# 2. Uploads it to [TestPyPI](https://test.pypi.org/).
# 3. Creates a temporary virtual environment.
# 4. Installs `proxima` from TestPyPI.
# 5. Installs the test dependencies from PyPI.
# 6. Runs the Python test suite.
# 7. Removes the temporary environment.
make publish-test TOKEN=pypi-<testpypi-token>
[!NOTE] TestPyPI does not allow a previously used distribution filename to be uploaded again, even if the previous release was deleted. If
0.1.0has already been uploaded, bump the version to0.1.1before publishing another build.
Publishing
Releases are published to PyPI through GitHub Actions.
Create a version tag :
git tag v0.1.1
git push origin v0.1.1
The release workflow :
- Builds wheels and the source distribution on Linux and macOS.
- Creates a GitHub Release.
- Publishes the distributions to PyPI.
The GitHub Actions workflow uses PyPI Trusted Publishing, so a PyPI API token is not required in repository secrets.
For local publishing, uv can be used directly:
uv publish \
--token "$PYPI_TOKEN" \
dist/*
[!NOTE] TestPyPI and PyPI use separate credentials. A TestPyPI token cannot be used to publish to PyPI.
Python Compatibility
Proxima uses nanobind's stable Python ABI:
cp312-abi3
The package targets Python 3.12+, allowing the same abi3 wheel to be used across supported Python versions on the same platform and architecture.
License
MIT
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distributions
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file proxima_hnsw-0.1.9.tar.gz.
File metadata
- Download URL: proxima_hnsw-0.1.9.tar.gz
- Upload date:
- Size: 70.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
uv/0.12.7 {"installer":{"name":"uv","version":"0.12.7","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3e761d99af9fad774a9df9f7ec3d60de6c4043f54e1f9761112d0e4fcbb0718f
|
|
| MD5 |
e2d8acf0c83aee4ad32ca2d577e71db2
|
|
| BLAKE2b-256 |
2a2c7f0acf5aa7c889fc986ccbed5be8b731f0df3fbb25284ff50807d64ba26b
|
File details
Details for the file proxima_hnsw-0.1.9-cp312-abi3-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl.
File metadata
- Download URL: proxima_hnsw-0.1.9-cp312-abi3-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl
- Upload date:
- Size: 93.4 kB
- Tags: CPython 3.12+, manylinux: glibc 2.27+ x86-64, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
uv/0.12.7 {"installer":{"name":"uv","version":"0.12.7","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e83e056ae1198263ebcb5ebcd32e5839611b3655208322a980047f29e4297108
|
|
| MD5 |
18b2dbdae16841800cfda43e1beb6ca4
|
|
| BLAKE2b-256 |
a9f558d08b9938488c4feb3aaa09945a75ff1e8b24353168cfc56fca34b33b5e
|
File details
Details for the file proxima_hnsw-0.1.9-cp312-abi3-macosx_11_0_arm64.whl.
File metadata
- Download URL: proxima_hnsw-0.1.9-cp312-abi3-macosx_11_0_arm64.whl
- Upload date:
- Size: 72.2 kB
- Tags: CPython 3.12+, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
uv/0.12.7 {"installer":{"name":"uv","version":"0.12.7","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6b7ec2ead07c22e62aaf9d2d0de3e565212a517a7dbeeb0ca1d3345df0c9e501
|
|
| MD5 |
c6191ed905bb706ab07cabc5332c863b
|
|
| BLAKE2b-256 |
0e8f9fb524a44825ad4af189f8c5bb48df3d8f7b5debe40ec5a1d0f86865ff54
|