Skip to main content

puggles

Fast multi-objective evolutionary optimization for Python — NSGA-II and NSGA-III, with a Rust core. Roughly 7–8× faster than pymoo and 20–30× faster than DEAP and platypus at equal solution quality.

pip install puggles

Prebuilt wheels for Linux, macOS, and Windows; Python 3.9+. No Rust toolchain needed.

Quick start

import puggles as pg

# ZDT1: two conflicting objectives over 10 variables in [0, 1].
def zdt1(x):
    g = 1 + 9 * sum(x[1:]) / (len(x) - 1)
    return [x[0], g * (1 - (x[0] / g) ** 0.5)]

problem = pg.Problem(
    solution_length=10,
    number_of_objectives=2,
    solution_data_types=[pg.Real(0.0, 1.0)] * 10,
    objective_function=zdt1,     # must return a LIST, one entry per objective
    direction=[-1, -1],          # -1 = minimize, 1 = maximize
)

ga = pg.NSGAII(problem, population_size=100, seed=42)
ga.run(10_000)                   # budget in objective-function evaluations

for s in ga.get_archive():       # the Pareto front
    print(s.variables, s.objectives)

Benchmarks

ZDT1, population 100, 10,000 evaluations, Apple M3. IGD lower is better — all libraries converge to the same quality, so the difference is pure algorithm overhead.

library ms / run IGD
puggles 31.8 0.0051
pymoo 215.4 0.0045
DEAP 843.4 0.0048
platypus 1062.1 0.0108

On DTLZ2 (3 objectives), NSGAIII reaches IGD 0.011 — the best of any library measured, against pymoo's 0.076.

Features

  • NSGA-II and NSGA-III (reference-point based; prefer it for 3+ objectives)
  • Real, Integer, and Binary decision variables, mixable in one problem
  • Constraints — objective bounds and decision-variable g(x) <= 0
  • Batch objectives — batch_objective_function=f evaluates a whole population per call, amortizing the GIL. ~1.8× on an expensive objective; a wash on a cheap one. Works with both NSGAII and NSGAIII.
  • Permutation encoding — permutation=True for ordering problems (TSP, scheduling); uses order crossover and swap mutation so solutions stay valid permutations.
  • Checkpoint & resume — ga.save_state() returns JSON, ga.load_state(s) restores it, so long runs survive a restart.
  • Front-quality metrics — hypervolume_2d, igd, spacing, and run_until_hv_converged(...) to stop when the front stops improving instead of at a fixed budget.
  • Island model — run_island_model(...) runs independent populations in parallel and merges their fronts (native Rust objectives only; the GIL would serialize Python callables).
  • Reproducible runs — seed=42 fixes the initial population, crossover, mutation, and selection, so a run repeats exactly. Omit it for fresh randomness each time.
  • GPU evaluation via GpuProblem and a WGSL compute shader (experimental)
  • Clear errors — invalid bounds or configuration raise ValueError, not a Rust panic.
  • Built-in DTLZ1–7 benchmark problems

Permutation example

import puggles as pg

POS = [0.0, 9.0, 3.0, 7.0, 1.0, 5.0, 8.0, 2.0]
tour = lambda x: [sum(abs(POS[int(a)] - POS[int(b)]) for a, b in zip(x, x[1:]))]

problem = pg.Problem(8, 1, [pg.Integer(0, 7)] * 8, tour, permutation=True)
ga = pg.NSGAII(problem, population_size=40, seed=5)
ga.run(6000)

best = min(ga.get_archive(), key=lambda s: s.objectives[0])
print(best.objectives[0], [int(v) for v in best.variables])

Reproducibility

A genetic algorithm is randomised: without a seed, two runs of identical code give different answers (on ZDT1, roughly 10% apart in IGD). Pass a seed to make a run exactly repeatable — essential for publishing a result, writing a regression test, or comparing two parameter settings without measuring noise.

a = pg.NSGAII(problem, seed=42); a.run(10_000)
b = pg.NSGAII(problem, seed=42); b.run(10_000)
# a and b produce identical fronts, down to the last bit

Seeding applies to NSGAIII too. Use it with execution_mode="sequential": multithreaded runs interleave evaluations non-deterministically, so they are not reproducible even when seeded.

Many objectives

ga = pg.NSGAIII(problem, divisions=12, seed=42)   # population derived from the reference points
ga.run(20_000)

Tuning operators

ga = pg.NSGAII(
    problem,
    population_size=100,
    crossover_config=pg.CrossoverConfig(real_crossover="sbx", sbx_distribution_index=20.0),
    mutation_config=pg.MutationConfig(real_mutation="polynomial"),  # probability=None -> 1/n
)

Leave probability at None unless you have a reason: it defaults to the conventional 1/n per-gene rate. A rate of 1.0 replaces the whole genome every generation, which is random search, not evolution.

Status

The NSGA-II core across all three encodings is well tested and benchmarked. The GPU evaluator is experimental and untested in CI. One Python-callable problem may be optimized at a time per process — concurrent GAs over different Python objectives in threads are not supported.

License

MIT OR Apache-2.0

Metadata

Release files for puggles 0.2.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for puggles 0.2.0
File Size Uploaded
puggles-0.2.0.tar.gz 107.7 kB Details

Built distributions (wheels)

Table of built distributions (wheels) for puggles 0.2.0
File
puggles-0.2.0-cp39-abi3-win_amd64.whl CPython 3.9 abi3 Windows x86-64 Details
puggles-0.2.0-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl CPython 3.9 abi3 Linux glibc 2.17+ x86-64 Details
puggles-0.2.0-cp39-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl CPython 3.9 abi3 Linux glibc 2.17+ ARM64 Details
puggles-0.2.0-cp39-abi3-macosx_11_0_arm64.whl CPython 3.9 abi3 macOS 11.0+ ARM64 Details
puggles-0.2.0-cp39-abi3-macosx_10_12_x86_64.whl CPython 3.9 abi3 macOS 10.12+ x86-64 Details

Total release size: 2.5 MB

Release files / puggles-0.2.0.tar.gz

Download URL puggles-0.2.0.tar.gz
Size 107.7 kB
Tags Source
SHA-256 checksum
How to use checksums
c4be6a75eed1daa0dba227e5dba85e8bff5d0b967b8717c7d9c843610f1fb3b7
BLAKE2b-256 checksum
How to use checksums
42915674922f7639933e017a5857d6ac46a255a6c7a5de231d7dd368d5d7cbf4
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.14

Release files / puggles-0.2.0-cp39-abi3-win_amd64.whl

Download URL puggles-0.2.0-cp39-abi3-win_amd64.whl
Size 398.6 kB
Tags CPython 3.9 Windows x86-64 abi3
SHA-256 checksum
How to use checksums
8f3152d9e8bd33f292bd6838dc42b37ccf65e9eb78894339e8b4c50abe74754a
BLAKE2b-256 checksum
How to use checksums
da14843ebde7f79c3b0e3b2291be71538306ddbaefcb6a7bdfa10e8896fe87ae
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.14

Release files / puggles-0.2.0-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl

Download URL puggles-0.2.0-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Size 525.3 kB
Tags CPython 3.9 Linux glibc 2.17+ x86-64 abi3
SHA-256 checksum
How to use checksums
500d624b07a6566b4be998174034920cadf6581c9b6ee4d45a25835c7a553551
BLAKE2b-256 checksum
How to use checksums
25e83a36adedb512a313dc1b5b8aeed101bb064fa60897511c3e4a30e1996a85
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.14

Release files / puggles-0.2.0-cp39-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl

Download URL puggles-0.2.0-cp39-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Size 512.6 kB
Tags CPython 3.9 Linux glibc 2.17+ ARM64 abi3
SHA-256 checksum
How to use checksums
a7ed1b3c337fdaac5c017308cc447c60e9e39191a882600f607ab89d3f8fda02
BLAKE2b-256 checksum
How to use checksums
0bb4af0d93c0d0cb139533ab0ea4ff57b283822db2236a77ed248c4b30c0a438
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.14

Release files / puggles-0.2.0-cp39-abi3-macosx_11_0_arm64.whl

Download URL puggles-0.2.0-cp39-abi3-macosx_11_0_arm64.whl
Size 473.2 kB
Tags CPython 3.9 abi3 macOS 11.0+ ARM64
SHA-256 checksum
How to use checksums
107ac5c02d394aea8f40e07353215aabb761bd6caa263fa933544c4dcc4b0c1b
BLAKE2b-256 checksum
How to use checksums
a262ae7b23afd21154bb35d04725534729648a5c10e9f1363587e01741eec63e
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.14

Release files / puggles-0.2.0-cp39-abi3-macosx_10_12_x86_64.whl

Download URL puggles-0.2.0-cp39-abi3-macosx_10_12_x86_64.whl
Size 496.3 kB
Tags CPython 3.9 abi3 macOS 10.12+ x86-64
SHA-256 checksum
How to use checksums
384ef798e26efa5c116cbaa1e91dba656065cc5575558cfe9ea4af6b88a74e86
BLAKE2b-256 checksum
How to use checksums
bc7cb0e727f993eed3c2ad1c67f2d43b55394078cc1c3ffa99f06f87ea9b6d26
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.13.14

Release history Release notifications | RSS feed

This release

0.2.0 This release

6 release files

0.1.0

6 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page