From 6f7358b8120e3765a6869e02aa302ec8ae4d5386 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:05:05 +0800 Subject: [PATCH 01/15] Design: recategorize problem models by input structure Current categorization mixes input structure (graph, set) with problem type (optimization, satisfaction). Reorganize into orthogonal categories based solely on input structure: graph/, formula/, set/, algebraic/, misc/. Co-Authored-By: Claude Opus 4.6 --- .claude/CLAUDE.md | 9 +- ...026-03-01-problem-categorization-design.md | 84 +++++++++++++++++++ 2 files changed, 91 insertions(+), 2 deletions(-) create mode 100644 docs/plans/2026-03-01-problem-categorization-design.md diff --git a/.claude/CLAUDE.md b/.claude/CLAUDE.md index 182d874f..dbd7a3ae 100644 --- a/.claude/CLAUDE.md +++ b/.claude/CLAUDE.md @@ -49,7 +49,12 @@ make release V=x.y.z # Tag and push a new release (CI publishes to crates.io) ## Architecture ### Core Modules -- `src/models/` - Problem implementations (SAT, Graph, Set, Optimization) +- `src/models/` - Problem implementations organized by input structure: + - `graph/` - Problems on graphs (MIS, MaxClique, MaxCut, MinVC, MinDS, MaxMatching, MaximalIS, KColoring, TSP, SpinGlass, BicliqueCover) + - `formula/` - Logical formulas and circuits (SAT, k-SAT, CircuitSAT) + - `set/` - Set systems (MinSetCovering, MaxSetPacking) + - `algebraic/` - Matrices, linear systems, lattices (QUBO, ILP, CVP, BMF) + - `misc/` - Unique input structures (BinPacking, PaintShop, Factoring) - `src/rules/` - Reduction rules + inventory registration - `src/solvers/` - BruteForce solver, ILP solver (feature-gated) - `src/traits.rs` - `Problem`, `OptimizationProblem`, `SatisfactionProblem` traits @@ -140,7 +145,7 @@ Reduction graph nodes use variant key-value pairs from `Problem::variant()`: ### File Naming - Reduction files: `src/rules/_.rs` (e.g., `maximumindependentset_qubo.rs`) -- Model files: `src/models//.rs` (e.g., `maximum_independent_set.rs`) +- Model files: `src/models//.rs` — category is by input structure: `graph/` (graph input), `formula/` (boolean formula/circuit), `set/` (universe + subsets), `algebraic/` (matrix/linear system/lattice), `misc/` (other) - Example files: `examples/reduction__to_.rs` (must have `pub fn run()` + `fn main() { run() }`) - Test naming: `test__to__closed_loop` diff --git a/docs/plans/2026-03-01-problem-categorization-design.md b/docs/plans/2026-03-01-problem-categorization-design.md new file mode 100644 index 00000000..4db0704f --- /dev/null +++ b/docs/plans/2026-03-01-problem-categorization-design.md @@ -0,0 +1,84 @@ +# Problem Categorization Redesign + +## Problem + +The current categorization mixes two axes: +- **Input structure** (graph, set system, formula) +- **Problem type** (optimization vs satisfaction) + +This creates ambiguity: MIS is both a graph problem and an optimization problem. QUBO is on a matrix but lives in `optimization/`. CircuitSAT is a satisfiability problem but lives in `specialized/`. The `specialized/` folder is a catch-all with no unifying principle. + +## Design + +**Single axis: primary input structure** — "what data type does the problem operate on?" + +The optimization/satisfaction distinction is already captured by the trait hierarchy (`OptimizationProblem` vs `SatisfactionProblem`), so folders should not duplicate it. + +### New folder structure + +``` +src/models/ +├── graph/ # Input: a graph (optionally weighted) +│ ├── maximum_independent_set.rs +│ ├── maximum_clique.rs +│ ├── max_cut.rs +│ ├── maximum_matching.rs +│ ├── minimum_vertex_cover.rs +│ ├── minimum_dominating_set.rs +│ ├── maximal_is.rs +│ ├── kcoloring.rs +│ ├── traveling_salesman.rs +│ ├── spin_glass.rs ← from optimization/ +│ └── biclique_cover.rs ← from specialized/ +│ +├── formula/ # Input: a logical formula or circuit +│ ├── sat.rs +│ ├── ksat.rs +│ └── circuit.rs ← from specialized/ +│ +├── set/ # Input: universe + collection of subsets +│ ├── minimum_set_covering.rs +│ └── maximum_set_packing.rs +│ +├── algebraic/ # Input: matrix, linear system, or lattice +│ ├── qubo.rs ← from optimization/ +│ ├── ilp.rs ← from optimization/ +│ ├── closest_vector_problem.rs ← from optimization/ +│ └── bmf.rs ← from specialized/ +│ +└── misc/ # Problems with unique input structures + ├── bin_packing.rs ← from optimization/ + ├── paintshop.rs ← from specialized/ + └── factoring.rs ← from specialized/ +``` + +### Decision rule for new problems + +> "What is the primary data structure in the struct definition?" +> - Graph → `graph/` +> - Boolean formula or circuit → `formula/` +> - Universe + subsets → `set/` +> - Matrix, linear system, or lattice → `algebraic/` +> - None of the above → `misc/` + +### What moves + +| Problem | From | To | Reason | +|---|---|---|---| +| SpinGlass | optimization/ | graph/ | Parameterized by G, operates on graph edges | +| BicliqueCover | specialized/ | graph/ | Input is a BipartiteGraph | +| CircuitSAT | specialized/ | formula/ | Input is a boolean circuit | +| QUBO | optimization/ | algebraic/ | Input is a Q matrix (no graph param) | +| ILP | optimization/ | algebraic/ | Input is constraint matrix + objective | +| CVP | optimization/ | algebraic/ | Input is lattice basis matrix | +| BMF | specialized/ | algebraic/ | Input is a boolean matrix | +| BinPacking | optimization/ | misc/ | Input is items + capacity | +| PaintShop | specialized/ | misc/ | Input is a car sequence | +| Factoring | specialized/ | misc/ | Input is an integer | + +### What doesn't change + +- Trait hierarchy (`OptimizationProblem`, `SatisfactionProblem`) +- All public API, type names, re-exports +- Only `mod.rs` files, `use` paths, and `#[path]` test references change +- The `optimization/` and `specialized/` folders are eliminated From 520fc5d29b9624ea3a4163f7afa8659093d688dc Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:12:07 +0800 Subject: [PATCH 02/15] Simplify contributor guide: file an issue, we implement it Lower the understanding barrier for contributors: - Lead with "no programming required" and a 3-step flow - Add community calls section (coming soon via Zulip) - Update reduction graph legend for new model categories - Update design.md module table for new category names Co-Authored-By: Claude Opus 4.6 --- README.md | 31 +++++++++++-------------------- docs/src/design.md | 2 +- docs/src/introduction.md | 27 +++++++++++++++++---------- 3 files changed, 29 insertions(+), 31 deletions(-) diff --git a/README.md b/README.md index 71ed753e..c9bc49a4 100644 --- a/README.md +++ b/README.md @@ -63,31 +63,22 @@ See the [MCP documentation](https://codingthrust.github.io/problem-reductions/mc ## Contributing -### Authorship Recognition +**No programming experience required.** You contribute domain knowledge; we handle the implementation. -**Contribute 10 non-trivial reduction rules and you will be automatically added to the author list of the paper.** AI tools handle the implementation — contributors focus on designing correct reductions and test cases. +1. **File an issue** — use the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Describe the problem or reduction you have in mind — the template guides you through the details. +2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested pull request. +3. **You review it** — you'll be mentioned on the PR to provide feedback. We present the implementation and iterate until you're satisfied. -### How to Contribute +**Community calls** (coming soon via [Zulip](https://zulip.com/)): all issue contributors will be invited. Maintainers walk through recent implementations so you can ask questions and give feedback in real time. -1. **Open an issue** using the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Fill in all sections — the templates guide you through the required information (definition, algorithm, size overhead, example instance, etc.). +**Authorship:** contribute 10 non-trivial reduction rules and you'll be added to the author list of the [paper](https://codingthrust.github.io/problem-reductions/reductions.pdf). - **Hint:** If you use Claude Code / OpenCode / Codex (assume `gh` CLI tool and `superpowers` plugin are installed), you can just type: - ``` - File an issue on CodingThrust/problem-reductions, using the "Model" issue template, about the Closest Vector Problem. Brainstorm with me. - ``` - ``` - File an issue on CodingThrust/problem-reductions, using the "Rule" issue template, about reduction from Closest Vector Problem to QUBO. Brainstorm with me. - ``` - Then AI agents will guide you to fill in the issue template. +> **Tip:** If you use Claude Code / OpenCode / Codex, you can file issues interactively: +> ``` +> File an issue on CodingThrust/problem-reductions, using the "Model" issue template, about the Closest Vector Problem. Brainstorm with me. +> ``` -2. Our AI agents will pick up the issue and generate a plan to implement the reduction rule. -3. You will be mentioned in the pull request, provide feedback to the AI agents. If you are satisfied with the plan, you can merge the PR. - -Optionally, if you prefer to **implement yourself**, I will recommend you to use the [superpowers:brainstorming](https://github.com/obra/superpowers) skill to help you write a detailed plan. Create a PR and let maintainers help review and merge the PR. - -### Developer Commands - -Run `make help` to see all available targets. See [CLAUDE.md](https://codingthrust.github.io/problem-reductions/claude.html) for the full command list and architecture details. +If you prefer to **implement yourself**, see the [Design](https://codingthrust.github.io/problem-reductions/design.html) guide. Run `make help` to see available developer commands. ## Acknowledgments diff --git a/docs/src/design.md b/docs/src/design.md index ef8ce6e8..dd2d7593 100644 --- a/docs/src/design.md +++ b/docs/src/design.md @@ -17,7 +17,7 @@ This guide covers the library internals for contributors. | Module | Purpose | |--------|---------| -| [`src/models/`](#problem-model) | Problem type implementations (SAT, Graph, Set, Optimization) | +| [`src/models/`](#problem-model) | Problem implementations by input structure: `graph/`, `formula/`, `set/`, `algebraic/`, `misc/` | | [`src/rules/`](#reduction-rules) | Reduction rules with `ReduceTo` implementations | | [`src/registry/`](#reduction-graph) | Reduction graph metadata (collected via `inventory`) | | [`src/solvers/`](#solvers) | BruteForce and ILP solvers | diff --git a/docs/src/introduction.md b/docs/src/introduction.md index 42b49d4e..d1571584 100644 --- a/docs/src/introduction.md +++ b/docs/src/introduction.md @@ -14,10 +14,10 @@
Graph + Formula Set - Optimization - Satisfiability - Specialized + Algebraic + Misc Variant Cast
@@ -62,14 +62,21 @@ This library is the foundation of that effort: an open-source, extensible reduct ## Call for Contributions -> **Everyone can contribute — no programming experience required.** If you know a computational problem or a reduction rule, just describe it in a GitHub issue. AI will generate a tested pull request for you to review. -> -> **Contribute 10 non-trivial reduction rules and you will be automatically added to the author list of the [paper](https://codingthrust.github.io/problem-reductions/reductions.pdf).** +> **No programming experience required.** You contribute domain knowledge — we handle the implementation. -1. **Open an issue** using the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template -2. **Fill in all sections** — definition, algorithm, size overhead, example instance -3. **Review AI-generated code** — AI generates code and you can comment on the pull request -4. **Merge** — ask maintainers' assistance to merge once you are satisfied +### How it works + +1. **File an issue** — use the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Describe the problem or reduction you have in mind; the template guides you through the details. +2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested pull request. +3. **You review it** — you'll be mentioned on the PR to provide feedback. We iterate until you're satisfied. + +### Community calls + +Coming soon via [Zulip](https://zulip.com/). All issue contributors will be invited. Maintainers walk through recent implementations so you can ask questions and give feedback in real time. + +### Authorship + +Contribute 10 non-trivial reduction rules and you'll be added to the author list of the [paper](https://codingthrust.github.io/problem-reductions/reductions.pdf). For manual implementation, see the [Design](./design.md#contributing) guide. From 290aeb171b9add6d20ef05b2e7d48d11dfe27ca1 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:13:02 +0800 Subject: [PATCH 03/15] Clarify contributor role: feedback via community calls, not code review Contributors provide feedback on documentation and CLI behavior during community calls with maintainers, rather than reviewing code on PRs. Co-Authored-By: Claude Opus 4.6 --- README.md | 6 ++---- docs/src/introduction.md | 8 ++------ 2 files changed, 4 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index c9bc49a4..03bee426 100644 --- a/README.md +++ b/README.md @@ -66,10 +66,8 @@ See the [MCP documentation](https://codingthrust.github.io/problem-reductions/mc **No programming experience required.** You contribute domain knowledge; we handle the implementation. 1. **File an issue** — use the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Describe the problem or reduction you have in mind — the template guides you through the details. -2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested pull request. -3. **You review it** — you'll be mentioned on the PR to provide feedback. We present the implementation and iterate until you're satisfied. - -**Community calls** (coming soon via [Zulip](https://zulip.com/)): all issue contributors will be invited. Maintainers walk through recent implementations so you can ask questions and give feedback in real time. +2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested implementation. +3. **We present it to you** — all issue contributors are invited to community calls (coming soon via [Zulip](https://zulip.com/)), where maintainers walk through the implementation — documentation, CLI behavior, correctness — and you provide feedback. **Authorship:** contribute 10 non-trivial reduction rules and you'll be added to the author list of the [paper](https://codingthrust.github.io/problem-reductions/reductions.pdf). diff --git a/docs/src/introduction.md b/docs/src/introduction.md index d1571584..3fa25eba 100644 --- a/docs/src/introduction.md +++ b/docs/src/introduction.md @@ -67,12 +67,8 @@ This library is the foundation of that effort: an open-source, extensible reduct ### How it works 1. **File an issue** — use the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Describe the problem or reduction you have in mind; the template guides you through the details. -2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested pull request. -3. **You review it** — you'll be mentioned on the PR to provide feedback. We iterate until you're satisfied. - -### Community calls - -Coming soon via [Zulip](https://zulip.com/). All issue contributors will be invited. Maintainers walk through recent implementations so you can ask questions and give feedback in real time. +2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested implementation. +3. **We present it to you** — all issue contributors are invited to community calls (coming soon via [Zulip](https://zulip.com/)), where maintainers walk through the implementation — documentation, CLI behavior, correctness — and you provide feedback. ### Authorship From 06db71595b77686f964466af5bbf5cf58c77379f Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:19:29 +0800 Subject: [PATCH 04/15] Add Zulip community link Replace placeholder with https://problem-reductions.zulipchat.com/ Co-Authored-By: Claude Opus 4.6 --- README.md | 2 +- docs/src/introduction.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 03bee426..a72c953f 100644 --- a/README.md +++ b/README.md @@ -67,7 +67,7 @@ See the [MCP documentation](https://codingthrust.github.io/problem-reductions/mc 1. **File an issue** — use the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Describe the problem or reduction you have in mind — the template guides you through the details. 2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested implementation. -3. **We present it to you** — all issue contributors are invited to community calls (coming soon via [Zulip](https://zulip.com/)), where maintainers walk through the implementation — documentation, CLI behavior, correctness — and you provide feedback. +3. **We present it to you** — all issue contributors are invited to community calls (via [Zulip](https://problem-reductions.zulipchat.com/)), where maintainers walk through the implementation — documentation, CLI behavior, correctness — and you provide feedback. **Authorship:** contribute 10 non-trivial reduction rules and you'll be added to the author list of the [paper](https://codingthrust.github.io/problem-reductions/reductions.pdf). diff --git a/docs/src/introduction.md b/docs/src/introduction.md index 3fa25eba..753a3a8f 100644 --- a/docs/src/introduction.md +++ b/docs/src/introduction.md @@ -68,7 +68,7 @@ This library is the foundation of that effort: an open-source, extensible reduct 1. **File an issue** — use the [Problem](https://github.com/CodingThrust/problem-reductions/issues/new?template=problem.md) or [Rule](https://github.com/CodingThrust/problem-reductions/issues/new?template=rule.md) template. Describe the problem or reduction you have in mind; the template guides you through the details. 2. **We implement it** — for reasonable requests, maintainers tag the issue `implement` and AI agents generate a tested implementation. -3. **We present it to you** — all issue contributors are invited to community calls (coming soon via [Zulip](https://zulip.com/)), where maintainers walk through the implementation — documentation, CLI behavior, correctness — and you provide feedback. +3. **We present it to you** — all issue contributors are invited to community calls (via [Zulip](https://problem-reductions.zulipchat.com/)), where maintainers walk through the implementation — documentation, CLI behavior, correctness — and you provide feedback. ### Authorship From 0dc7894f9d7a6d5f9448421e5b55d79f9339e21b Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:22:05 +0800 Subject: [PATCH 05/15] Add implementation plan for problem categorization refactoring 10-task plan covering file moves, mod.rs updates, import fixes across rules/examples/tests/docs, visualization colors, and artifact regeneration. Co-Authored-By: Claude Opus 4.6 --- .../2026-03-01-problem-categorization-impl.md | 618 ++++++++++++++++++ 1 file changed, 618 insertions(+) create mode 100644 docs/plans/2026-03-01-problem-categorization-impl.md diff --git a/docs/plans/2026-03-01-problem-categorization-impl.md b/docs/plans/2026-03-01-problem-categorization-impl.md new file mode 100644 index 00000000..7654661a --- /dev/null +++ b/docs/plans/2026-03-01-problem-categorization-impl.md @@ -0,0 +1,618 @@ +# Problem Categorization Refactoring Implementation Plan + +> **For Claude:** REQUIRED SUB-SKILL: Use superpowers:executing-plans to implement this plan task-by-task. + +**Goal:** Move problem model files from the old mixed-axis categories (`optimization/`, `satisfiability/`, `specialized/`) to new input-structure-based categories (`formula/`, `algebraic/`, `misc/`), keeping `graph/` and `set/` unchanged. + +**Architecture:** Pure file-move refactoring. The `classify_problem_category()` function in `src/rules/graph.rs` automatically derives categories from `module_path!()`, so moving files is sufficient — no classification logic changes. The `graph/` and `set/` modules are untouched. The `satisfiability/` module is renamed to `formula/` (with CircuitSAT added). The `optimization/` and `specialized/` modules are eliminated. + +**Tech Stack:** Rust, `git mv`, `make check` + +**Key reference:** Design doc at `docs/plans/2026-03-01-problem-categorization-design.md` + +--- + +### Task 1: Create new module directories and move source files + +**Files:** +- Create: `src/models/formula/mod.rs`, `src/models/algebraic/mod.rs`, `src/models/misc/mod.rs` +- Move (git mv): 13 source files between directories +- Delete: `src/models/optimization/`, `src/models/satisfiability/`, `src/models/specialized/` (after moves) + +**Step 1: Move satisfiability/ → formula/ (rename + add CircuitSAT)** + +```bash +# Rename the directory +git mv src/models/satisfiability src/models/formula + +# Move CircuitSAT from specialized/ to formula/ +git mv src/models/specialized/circuit.rs src/models/formula/circuit.rs +``` + +**Step 2: Create algebraic/ and move files into it** + +```bash +mkdir -p src/models/algebraic + +git mv src/models/optimization/qubo.rs src/models/algebraic/qubo.rs +git mv src/models/optimization/ilp.rs src/models/algebraic/ilp.rs +git mv src/models/optimization/closest_vector_problem.rs src/models/algebraic/closest_vector_problem.rs +git mv src/models/specialized/bmf.rs src/models/algebraic/bmf.rs +``` + +**Step 3: Create misc/ and move files into it** + +```bash +mkdir -p src/models/misc + +git mv src/models/optimization/bin_packing.rs src/models/misc/bin_packing.rs +git mv src/models/specialized/factoring.rs src/models/misc/factoring.rs +git mv src/models/specialized/paintshop.rs src/models/misc/paintshop.rs +``` + +**Step 4: Move SpinGlass and BicliqueCover into graph/** + +```bash +git mv src/models/optimization/spin_glass.rs src/models/graph/spin_glass.rs +git mv src/models/specialized/biclique_cover.rs src/models/graph/biclique_cover.rs +``` + +**Step 5: Remove now-empty old directories** + +```bash +# optimization/ and specialized/ should be empty except for mod.rs +rm src/models/optimization/mod.rs +rmdir src/models/optimization +rm src/models/specialized/mod.rs +rmdir src/models/specialized +``` + +**Step 6: Commit** + +```bash +git add -A src/models/ +git commit -m "refactor: move model files to input-structure-based categories" +``` + +--- + +### Task 2: Update mod.rs files for new module structure + +**Files:** +- Modify: `src/models/mod.rs` +- Modify: `src/models/formula/mod.rs` (was satisfiability/mod.rs) +- Create: `src/models/algebraic/mod.rs` +- Create: `src/models/misc/mod.rs` +- Modify: `src/models/graph/mod.rs` + +**Step 1: Update `src/models/mod.rs`** + +Replace entire contents with: + +```rust +//! Problem model implementations. +//! +//! Each sub-module groups related problem types by input structure. + +pub mod algebraic; +pub mod formula; +pub mod graph; +pub mod misc; +pub mod set; + +// Re-export commonly used types +pub use algebraic::{BinPacking, ClosestVectorProblem, SpinGlass, ILP, QUBO}; +pub use formula::{CNFClause, KSatisfiability, Satisfiability}; +pub use graph::{ + KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, + MinimumDominatingSet, MinimumVertexCover, TravelingSalesman, +}; +pub use set::{MaximumSetPacking, MinimumSetCovering}; +pub use specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; +``` + +Wait — re-exports need to come from the *new* modules. Correct version: + +```rust +//! Problem model implementations. +//! +//! Each sub-module groups related problem types by input structure. + +pub mod algebraic; +pub mod formula; +pub mod graph; +pub mod misc; +pub mod set; + +// Re-export commonly used types +pub use algebraic::{ClosestVectorProblem, ILP, QUBO, BMF}; +pub use formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; +pub use graph::{ + BicliqueCover, KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, + MaximumMatching, MinimumDominatingSet, MinimumVertexCover, SpinGlass, TravelingSalesman, +}; +pub use misc::{BinPacking, Factoring, PaintShop}; +pub use set::{MaximumSetPacking, MinimumSetCovering}; +``` + +**Step 2: Update `src/models/formula/mod.rs` (was satisfiability/mod.rs)** + +Replace entire contents with: + +```rust +//! Logic and formula problems. +//! +//! Problems whose input is a boolean formula or circuit: +//! - [`Satisfiability`]: Boolean satisfiability (SAT) with CNF clauses +//! - [`KSatisfiability`]: K-SAT where each clause has exactly K literals +//! - [`CircuitSAT`]: Boolean circuit satisfiability + +mod ksat; +mod sat; +pub(crate) mod circuit; + +pub use circuit::{Assignment, BooleanExpr, BooleanOp, Circuit, CircuitSAT}; +pub use ksat::KSatisfiability; +pub use sat::{CNFClause, Satisfiability}; +``` + +**Step 3: Write `src/models/algebraic/mod.rs`** + +```rust +//! Algebraic problems. +//! +//! Problems whose input is a matrix, linear system, or lattice: +//! - [`QUBO`]: Quadratic Unconstrained Binary Optimization +//! - [`ILP`]: Integer Linear Programming +//! - [`ClosestVectorProblem`]: Closest Vector Problem (minimize lattice distance) +//! - [`BMF`]: Boolean Matrix Factorization + +pub(crate) mod bmf; +mod closest_vector_problem; +mod ilp; +mod qubo; + +pub use bmf::BMF; +pub use closest_vector_problem::ClosestVectorProblem; +pub use ilp::{Comparison, LinearConstraint, ObjectiveSense, VarBounds, ILP}; +pub use qubo::QUBO; +``` + +**Step 4: Write `src/models/misc/mod.rs`** + +```rust +//! Miscellaneous problems. +//! +//! Problems with unique input structures that don't fit other categories: +//! - [`BinPacking`]: Bin Packing (minimize bins) +//! - [`Factoring`]: Integer factorization +//! - [`PaintShop`]: Minimize color switches in paint shop scheduling + +mod bin_packing; +pub(crate) mod factoring; +pub(crate) mod paintshop; + +pub use bin_packing::BinPacking; +pub use factoring::Factoring; +pub use paintshop::PaintShop; +``` + +**Step 5: Update `src/models/graph/mod.rs`** — add SpinGlass and BicliqueCover + +Add to the module declarations (maintaining alphabetical order and `pub(crate)` visibility where the old modules used it): + +```rust +//! Graph problems. +//! +//! Problems whose input is a graph (optionally weighted): +//! - [`MaximumIndependentSet`]: Maximum weight independent set +//! - [`MaximalIS`]: Maximal independent set +//! - [`MinimumVertexCover`]: Minimum weight vertex cover +//! - [`MinimumDominatingSet`]: Minimum dominating set +//! - [`MaximumClique`]: Maximum weight clique +//! - [`MaxCut`]: Maximum cut on weighted graphs +//! - [`KColoring`]: K-vertex coloring +//! - [`MaximumMatching`]: Maximum weight matching +//! - [`TravelingSalesman`]: Traveling Salesman (minimum weight Hamiltonian cycle) +//! - [`SpinGlass`]: Ising model Hamiltonian +//! - [`BicliqueCover`]: Biclique cover on bipartite graphs + +pub(crate) mod biclique_cover; +pub(crate) mod kcoloring; +pub(crate) mod max_cut; +pub(crate) mod maximal_is; +pub(crate) mod maximum_clique; +pub(crate) mod maximum_independent_set; +pub(crate) mod maximum_matching; +pub(crate) mod minimum_dominating_set; +pub(crate) mod minimum_vertex_cover; +pub(crate) mod spin_glass; +pub(crate) mod traveling_salesman; + +pub use biclique_cover::BicliqueCover; +pub use kcoloring::KColoring; +pub use max_cut::MaxCut; +pub use maximal_is::MaximalIS; +pub use maximum_clique::MaximumClique; +pub use maximum_independent_set::MaximumIndependentSet; +pub use maximum_matching::MaximumMatching; +pub use minimum_dominating_set::MinimumDominatingSet; +pub use minimum_vertex_cover::MinimumVertexCover; +pub use spin_glass::SpinGlass; +pub use traveling_salesman::TravelingSalesman; +``` + +**Step 6: Commit** + +```bash +git add src/models/ +git commit -m "refactor: update mod.rs files for new category structure" +``` + +--- + +### Task 3: Move unit test files to match new source structure + +The unit tests mirror the source directory layout under `src/unit_tests/models/`. + +**Files:** +- Move: 12 unit test files to new directories +- Create: `src/unit_tests/models/formula/`, `src/unit_tests/models/algebraic/`, `src/unit_tests/models/misc/` + +**Step 1: Move test files** + +```bash +# formula/ (rename satisfiability/ + add circuit) +git mv src/unit_tests/models/satisfiability src/unit_tests/models/formula +git mv src/unit_tests/models/specialized/circuit.rs src/unit_tests/models/formula/circuit.rs + +# algebraic/ +mkdir -p src/unit_tests/models/algebraic +git mv src/unit_tests/models/optimization/qubo.rs src/unit_tests/models/algebraic/qubo.rs +git mv src/unit_tests/models/optimization/ilp.rs src/unit_tests/models/algebraic/ilp.rs +git mv src/unit_tests/models/optimization/closest_vector_problem.rs src/unit_tests/models/algebraic/closest_vector_problem.rs +git mv src/unit_tests/models/specialized/bmf.rs src/unit_tests/models/algebraic/bmf.rs + +# misc/ +mkdir -p src/unit_tests/models/misc +git mv src/unit_tests/models/optimization/bin_packing.rs src/unit_tests/models/misc/bin_packing.rs +git mv src/unit_tests/models/specialized/factoring.rs src/unit_tests/models/misc/factoring.rs +git mv src/unit_tests/models/specialized/paintshop.rs src/unit_tests/models/misc/paintshop.rs + +# graph/ (add spin_glass and biclique_cover) +git mv src/unit_tests/models/optimization/spin_glass.rs src/unit_tests/models/graph/spin_glass.rs +git mv src/unit_tests/models/specialized/biclique_cover.rs src/unit_tests/models/graph/biclique_cover.rs + +# Remove empty old directories +rmdir src/unit_tests/models/optimization +rmdir src/unit_tests/models/specialized +``` + +**Step 2: Update `#[path]` attributes in moved source files** + +Each model source file has a `#[cfg(test)] #[path = "..."]` attribute pointing to its test file. After the moves, these relative paths are still correct because both source and test moved by the same amount — **except** for files that changed category (e.g., spin_glass moved from `optimization/` to `graph/`). + +Update these `#[path]` attributes in the **source** files: + +| Source file (new location) | Old `#[path]` | New `#[path]` | +|---|---|---| +| `src/models/formula/sat.rs` | `../../unit_tests/models/satisfiability/sat.rs` | `../../unit_tests/models/formula/sat.rs` | +| `src/models/formula/ksat.rs` | `../../unit_tests/models/satisfiability/ksat.rs` | `../../unit_tests/models/formula/ksat.rs` | +| `src/models/formula/circuit.rs` | `../../unit_tests/models/specialized/circuit.rs` | `../../unit_tests/models/formula/circuit.rs` | +| `src/models/algebraic/qubo.rs` | `../../unit_tests/models/optimization/qubo.rs` | `../../unit_tests/models/algebraic/qubo.rs` | +| `src/models/algebraic/ilp.rs` | `../../unit_tests/models/optimization/ilp.rs` | `../../unit_tests/models/algebraic/ilp.rs` | +| `src/models/algebraic/closest_vector_problem.rs` | `../../unit_tests/models/optimization/closest_vector_problem.rs` | `../../unit_tests/models/algebraic/closest_vector_problem.rs` | +| `src/models/algebraic/bmf.rs` | `../../unit_tests/models/specialized/bmf.rs` | `../../unit_tests/models/algebraic/bmf.rs` | +| `src/models/misc/bin_packing.rs` | `../../unit_tests/models/optimization/bin_packing.rs` | `../../unit_tests/models/misc/bin_packing.rs` | +| `src/models/misc/factoring.rs` | `../../unit_tests/models/specialized/factoring.rs` | `../../unit_tests/models/misc/factoring.rs` | +| `src/models/misc/paintshop.rs` | `../../unit_tests/models/specialized/paintshop.rs` | `../../unit_tests/models/misc/paintshop.rs` | +| `src/models/graph/spin_glass.rs` | `../../unit_tests/models/optimization/spin_glass.rs` | `../../unit_tests/models/graph/spin_glass.rs` | +| `src/models/graph/biclique_cover.rs` | `../../unit_tests/models/specialized/biclique_cover.rs` | `../../unit_tests/models/graph/biclique_cover.rs` | + +Use grep to find the exact `#[path` line in each file and update it. + +**Step 3: Commit** + +```bash +git add -A src/unit_tests/models/ src/models/ +git commit -m "refactor: move unit tests to match new category structure" +``` + +--- + +### Task 4: Update all `use` imports in `src/rules/` + +Every reduction rule file imports problem types via `crate::models::::...`. These must be updated to the new category paths. + +**Files:** ~27 files in `src/rules/` + +**Replacements (find and replace across all files in `src/rules/`):** + +| Old import path | New import path | +|---|---| +| `crate::models::optimization::SpinGlass` | `crate::models::graph::SpinGlass` | +| `crate::models::optimization::QUBO` | `crate::models::algebraic::QUBO` | +| `crate::models::optimization::{...ILP...}` | `crate::models::algebraic::{...ILP...}` | +| `crate::models::optimization::BinPacking` | `crate::models::misc::BinPacking` | +| `crate::models::optimization::ClosestVectorProblem` | `crate::models::algebraic::ClosestVectorProblem` | +| `crate::models::satisfiability::Satisfiability` | `crate::models::formula::Satisfiability` | +| `crate::models::satisfiability::KSatisfiability` | `crate::models::formula::KSatisfiability` | +| `crate::models::satisfiability::{CNFClause, ...}` | `crate::models::formula::{CNFClause, ...}` | +| `crate::models::specialized::CircuitSAT` | `crate::models::formula::CircuitSAT` | +| `crate::models::specialized::{Assignment, BooleanExpr, ...Circuit...}` | `crate::models::formula::{Assignment, BooleanExpr, ...Circuit...}` | +| `crate::models::specialized::Factoring` | `crate::models::misc::Factoring` | +| `crate::models::specialized::PaintShop` | `crate::models::misc::PaintShop` | +| `crate::models::specialized::BicliqueCover` | `crate::models::graph::BicliqueCover` | +| `crate::models::specialized::BMF` | `crate::models::algebraic::BMF` | + +**Approach:** For each file in `src/rules/`, read it, identify any `use crate::models::{optimization,satisfiability,specialized}` lines, and update them. Many files import from multiple old categories, so some may need imports split into multiple `use` statements. + +Specific files to update (grouped by what they import): + +**ILP imports (optimization → algebraic):** `ilp_qubo.rs`, `qubo_ilp.rs`, `minimumsetcovering_ilp.rs`, `minimumvertexcover_ilp.rs`, `maximummatching_ilp.rs`, `circuit_ilp.rs`, `coloring_ilp.rs`, `maximumclique_ilp.rs`, `maximumindependentset_ilp.rs`, `maximumsetpacking_ilp.rs`, `travelingsalesman_ilp.rs`, `minimumdominatingset_ilp.rs`, `factoring_ilp.rs` + +**QUBO imports (optimization → algebraic):** `spinglass_qubo.rs`, `maximumsetpacking_qubo.rs`, `ksatisfiability_qubo.rs`, `minimumvertexcover_qubo.rs`, `maximumindependentset_qubo.rs`, `coloring_qubo.rs`, `ilp_qubo.rs` + +**SpinGlass imports (optimization → graph):** `spinglass_qubo.rs`, `spinglass_maxcut.rs`, `spinglass_casts.rs`, `circuit_spinglass.rs` + +**Satisfiability imports (satisfiability → formula):** `sat_coloring.rs`, `sat_ksat.rs`, `sat_maximumindependentset.rs`, `sat_minimumdominatingset.rs`, `sat_circuitsat.rs`, `ksatisfiability_qubo.rs`, `ksatisfiability_casts.rs` + +**CircuitSAT/Circuit imports (specialized → formula):** `circuit_spinglass.rs`, `circuit_ilp.rs`, `factoring_circuit.rs`, `sat_circuitsat.rs` + +**Factoring imports (specialized → misc):** `factoring_circuit.rs`, `factoring_ilp.rs` + +**Step: Commit** + +```bash +git add src/rules/ +git commit -m "refactor: update rule imports for new model categories" +``` + +--- + +### Task 5: Update `src/lib.rs` prelude and doc comments + +**Files:** +- Modify: `src/lib.rs` + +**Step 1: Update the API overview doc comment (line 10)** + +Change: +```rust +//! | [`models`] | Problem types — [`graph`](models::graph), [`satisfiability`](models::satisfiability), [`set`](models::set), [`optimization`](models::optimization), [`specialized`](models::specialized) | +``` +To: +```rust +//! | [`models`] | Problem types — [`graph`](models::graph), [`formula`](models::formula), [`set`](models::set), [`algebraic`](models::algebraic), [`misc`](models::misc) | +``` + +**Step 2: Update the prelude module (lines 43-46)** + +Change: +```rust + pub use crate::models::optimization::{SpinGlass, QUBO}; + pub use crate::models::satisfiability::{CNFClause, KSatisfiability, Satisfiability}; + pub use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; + pub use crate::models::specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; +``` +To: +```rust + pub use crate::models::algebraic::{QUBO, BMF}; + pub use crate::models::formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; + pub use crate::models::graph::{BicliqueCover, SpinGlass}; + pub use crate::models::misc::{BinPacking, Factoring, PaintShop}; + pub use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; +``` + +**Step 3: Commit** + +```bash +git add src/lib.rs +git commit -m "refactor: update lib.rs prelude and docs for new categories" +``` + +--- + +### Task 6: Update test imports and category assertions + +**Files:** +- Modify: `tests/suites/integration.rs` +- Modify: `tests/suites/reductions.rs` +- Modify: `src/unit_tests/rules/graph.rs` + +**Step 1: Update `tests/suites/integration.rs` (lines 7-10)** + +Change: +```rust +use problemreductions::models::optimization::*; +use problemreductions::models::satisfiability::*; +use problemreductions::models::set::*; +use problemreductions::models::specialized::*; +``` +To: +```rust +use problemreductions::models::algebraic::*; +use problemreductions::models::formula::*; +use problemreductions::models::misc::*; +use problemreductions::models::set::*; +``` + +**Step 2: Update `tests/suites/reductions.rs` (line 6)** + +Change: +```rust +use problemreductions::models::optimization::{LinearConstraint, ObjectiveSense, ILP}; +``` +To: +```rust +use problemreductions::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}; +``` + +**Step 3: Update category assertions in `src/unit_tests/rules/graph.rs`** + +| Line | Old assertion | New assertion | +|------|---|---| +| 219 | `n.category == "optimization"` | `n.category == "algebraic"` | +| 271-272 | `"optimization"` | `"algebraic"` | +| 275-276 | `"satisfiability"` | `"formula"` | +| 281-282 | `"specialized"` | `"misc"` | +| 397 | `categories.contains("optimization")` | `categories.contains("algebraic")` | +| 398 | `categories.contains("satisfiability")` | `categories.contains("formula")` | +| 399 | `categories.contains("specialized")` | `categories.contains("misc")` | +| 502 | `circuit.category, "specialized"` | `circuit.category, "formula"` | +| 782-783 | `"satisfiability"` | `"formula"` | +| 790-791 | `"optimization"` | `"algebraic"` | + +Also update the module path strings in the test assertions (lines 270-282): +- `"problemreductions::models::optimization::qubo"` → `"problemreductions::models::algebraic::qubo"` +- `"problemreductions::models::satisfiability::sat"` → `"problemreductions::models::formula::sat"` +- `"problemreductions::models::specialized::factoring"` → `"problemreductions::models::misc::factoring"` + +And in `test_classify_problem_category` (lines 781-791): +- `"problemreductions::models::satisfiability::satisfiability"` → `"problemreductions::models::formula::satisfiability"` +- `"problemreductions::models::optimization::qubo"` → `"problemreductions::models::algebraic::qubo"` + +**Step 4: Commit** + +```bash +git add tests/ src/unit_tests/ +git commit -m "refactor: update test imports and category assertions" +``` + +--- + +### Task 7: Update example imports + +**Files:** ~15 files in `examples/` + +**Replacements:** + +| Old import | New import | +|---|---| +| `problemreductions::models::optimization::ILP` | `problemreductions::models::algebraic::ILP` | +| `problemreductions::models::optimization::{LinearConstraint, ObjectiveSense, ILP}` | `problemreductions::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}` | +| `problemreductions::models::specialized::{Assignment, BooleanExpr, Circuit}` | `problemreductions::models::formula::{Assignment, BooleanExpr, Circuit}` | +| `problemreductions::models::specialized::{Assignment, BooleanExpr, Circuit, CircuitSAT}` | `problemreductions::models::formula::{Assignment, BooleanExpr, Circuit, CircuitSAT}` | + +Affected example files: +- All `reduction_*_to_ilp.rs` files (ILP import) +- `reduction_ilp_to_qubo.rs` (ILP import) +- `reduction_circuitsat_to_ilp.rs` (ILP + Circuit imports) +- `reduction_factoring_to_circuitsat.rs` (Circuit import) +- `reduction_circuitsat_to_spinglass.rs` (Circuit import) + +**Step: Commit** + +```bash +git add examples/ +git commit -m "refactor: update example imports for new categories" +``` + +--- + +### Task 8: Update documentation references + +**Files:** +- Modify: `docs/src/getting-started.md` (line 42) +- Modify: `docs/src/design.md` (module overview table) + +**Step 1: Update `docs/src/getting-started.md`** + +Change: +```rust +use problemreductions::models::optimization::ILP; +``` +To: +```rust +use problemreductions::models::algebraic::ILP; +``` + +**Step 2: Update `docs/src/design.md` module table** (already done partially in earlier commit — verify the line is correct) + +**Step 3: Commit** + +```bash +git add docs/ +git commit -m "docs: update import paths in getting-started guide" +``` + +--- + +### Task 9: Update reduction graph visualization colors + +**Files:** +- Modify: `docs/src/static/reduction-graph.js` (lines 16-23) + +**Step 1: Update `categoryColors` and `categoryBorders`** + +Change: +```javascript +var categoryColors = { + graph: '#c8f0c8', set: '#f0c8c8', optimization: '#f0f0a0', + satisfiability: '#c8c8f0', specialized: '#f0c8e0' +}; +var categoryBorders = { + graph: '#4a8c4a', set: '#8c4a4a', optimization: '#8c8c4a', + satisfiability: '#4a4a8c', specialized: '#8c4a6a' +}; +``` +To: +```javascript +var categoryColors = { + graph: '#c8f0c8', set: '#f0c8c8', algebraic: '#f0f0a0', + formula: '#c8c8f0', misc: '#f0c8e0' +}; +var categoryBorders = { + graph: '#4a8c4a', set: '#8c4a4a', algebraic: '#8c8c4a', + formula: '#4a4a8c', misc: '#8c4a6a' +}; +``` + +**Step 2: Commit** + +```bash +git add docs/src/static/reduction-graph.js +git commit -m "docs: update reduction graph colors for new categories" +``` + +--- + +### Task 10: Build, test, and regenerate artifacts + +**Step 1: Run `make check` to verify everything compiles and passes** + +```bash +make check +``` + +Expected: All fmt, clippy, and test checks pass. If there are compilation errors, they will point to remaining old import paths that were missed — fix them. + +**Step 2: Regenerate the reduction graph JSON (categories are derived from module paths)** + +```bash +cargo run --example export_graph +cargo run --example export_schemas +``` + +This regenerates `docs/src/reductions/reduction_graph.json` and `docs/src/reductions/problem_schemas.json` with the new category values. + +**Step 3: Build mdbook to verify visualization** + +```bash +make doc +``` + +**Step 4: Commit regenerated artifacts** + +```bash +git add docs/src/reductions/ docs/book/ +git commit -m "chore: regenerate reduction graph with new categories" +``` + +**Step 5: Run full test suite one final time** + +```bash +make check +``` + +Expected: All green. From b9d94393b39de3c54aa807217e6c68bc09d5a048 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:24:38 +0800 Subject: [PATCH 06/15] refactor: move model files to input-structure-based categories Co-Authored-By: Claude Opus 4.6 --- src/models/{specialized => algebraic}/bmf.rs | 0 .../closest_vector_problem.rs | 0 src/models/{optimization => algebraic}/ilp.rs | 0 .../{optimization => algebraic}/qubo.rs | 0 .../{specialized => formula}/circuit.rs | 0 .../{satisfiability => formula}/ksat.rs | 0 src/models/{satisfiability => formula}/mod.rs | 0 src/models/{satisfiability => formula}/sat.rs | 0 .../{specialized => graph}/biclique_cover.rs | 0 .../{optimization => graph}/spin_glass.rs | 0 .../{optimization => misc}/bin_packing.rs | 0 src/models/{specialized => misc}/factoring.rs | 0 src/models/{specialized => misc}/paintshop.rs | 0 src/models/optimization/mod.rs | 20 ------------------- src/models/specialized/mod.rs | 20 ------------------- 15 files changed, 40 deletions(-) rename src/models/{specialized => algebraic}/bmf.rs (100%) rename src/models/{optimization => algebraic}/closest_vector_problem.rs (100%) rename src/models/{optimization => algebraic}/ilp.rs (100%) rename src/models/{optimization => algebraic}/qubo.rs (100%) rename src/models/{specialized => formula}/circuit.rs (100%) rename src/models/{satisfiability => formula}/ksat.rs (100%) rename src/models/{satisfiability => formula}/mod.rs (100%) rename src/models/{satisfiability => formula}/sat.rs (100%) rename src/models/{specialized => graph}/biclique_cover.rs (100%) rename src/models/{optimization => graph}/spin_glass.rs (100%) rename src/models/{optimization => misc}/bin_packing.rs (100%) rename src/models/{specialized => misc}/factoring.rs (100%) rename src/models/{specialized => misc}/paintshop.rs (100%) delete mode 100644 src/models/optimization/mod.rs delete mode 100644 src/models/specialized/mod.rs diff --git a/src/models/specialized/bmf.rs b/src/models/algebraic/bmf.rs similarity index 100% rename from src/models/specialized/bmf.rs rename to src/models/algebraic/bmf.rs diff --git a/src/models/optimization/closest_vector_problem.rs b/src/models/algebraic/closest_vector_problem.rs similarity index 100% rename from src/models/optimization/closest_vector_problem.rs rename to src/models/algebraic/closest_vector_problem.rs diff --git a/src/models/optimization/ilp.rs b/src/models/algebraic/ilp.rs similarity index 100% rename from src/models/optimization/ilp.rs rename to src/models/algebraic/ilp.rs diff --git a/src/models/optimization/qubo.rs b/src/models/algebraic/qubo.rs similarity index 100% rename from src/models/optimization/qubo.rs rename to src/models/algebraic/qubo.rs diff --git a/src/models/specialized/circuit.rs b/src/models/formula/circuit.rs similarity index 100% rename from src/models/specialized/circuit.rs rename to src/models/formula/circuit.rs diff --git a/src/models/satisfiability/ksat.rs b/src/models/formula/ksat.rs similarity index 100% rename from src/models/satisfiability/ksat.rs rename to src/models/formula/ksat.rs diff --git a/src/models/satisfiability/mod.rs b/src/models/formula/mod.rs similarity index 100% rename from src/models/satisfiability/mod.rs rename to src/models/formula/mod.rs diff --git a/src/models/satisfiability/sat.rs b/src/models/formula/sat.rs similarity index 100% rename from src/models/satisfiability/sat.rs rename to src/models/formula/sat.rs diff --git a/src/models/specialized/biclique_cover.rs b/src/models/graph/biclique_cover.rs similarity index 100% rename from src/models/specialized/biclique_cover.rs rename to src/models/graph/biclique_cover.rs diff --git a/src/models/optimization/spin_glass.rs b/src/models/graph/spin_glass.rs similarity index 100% rename from src/models/optimization/spin_glass.rs rename to src/models/graph/spin_glass.rs diff --git a/src/models/optimization/bin_packing.rs b/src/models/misc/bin_packing.rs similarity index 100% rename from src/models/optimization/bin_packing.rs rename to src/models/misc/bin_packing.rs diff --git a/src/models/specialized/factoring.rs b/src/models/misc/factoring.rs similarity index 100% rename from src/models/specialized/factoring.rs rename to src/models/misc/factoring.rs diff --git a/src/models/specialized/paintshop.rs b/src/models/misc/paintshop.rs similarity index 100% rename from src/models/specialized/paintshop.rs rename to src/models/misc/paintshop.rs diff --git a/src/models/optimization/mod.rs b/src/models/optimization/mod.rs deleted file mode 100644 index b4feffe0..00000000 --- a/src/models/optimization/mod.rs +++ /dev/null @@ -1,20 +0,0 @@ -//! Optimization problems. -//! -//! This module contains optimization problems: -//! - [`BinPacking`]: Bin Packing (minimize bins) -//! - [`ClosestVectorProblem`]: Closest Vector Problem (minimize lattice distance) -//! - [`SpinGlass`]: Ising model Hamiltonian -//! - [`QUBO`]: Quadratic Unconstrained Binary Optimization -//! - [`ILP`]: Integer Linear Programming - -mod bin_packing; -mod closest_vector_problem; -mod ilp; -mod qubo; -mod spin_glass; - -pub use bin_packing::BinPacking; -pub use closest_vector_problem::ClosestVectorProblem; -pub use ilp::{Comparison, LinearConstraint, ObjectiveSense, VarBounds, ILP}; -pub use qubo::QUBO; -pub use spin_glass::SpinGlass; diff --git a/src/models/specialized/mod.rs b/src/models/specialized/mod.rs deleted file mode 100644 index 63b70c68..00000000 --- a/src/models/specialized/mod.rs +++ /dev/null @@ -1,20 +0,0 @@ -//! Specialized NP-hard problems. -//! -//! This module contains problems that don't fit neatly into other categories: -//! - [`CircuitSAT`]: Boolean circuit satisfiability -//! - [`Factoring`]: Integer factorization -//! - [`PaintShop`]: Minimize color switches in paint shop scheduling -//! - [`BicliqueCover`]: Biclique cover on bipartite graphs -//! - [`BMF`]: Boolean matrix factorization - -pub(crate) mod biclique_cover; -pub(crate) mod bmf; -pub(crate) mod circuit; -pub(crate) mod factoring; -pub(crate) mod paintshop; - -pub use biclique_cover::BicliqueCover; -pub use bmf::BMF; -pub use circuit::{Assignment, BooleanExpr, BooleanOp, Circuit, CircuitSAT}; -pub use factoring::Factoring; -pub use paintshop::PaintShop; From 0a62200b8e70d8d1303e2c3e17c9ca25f29342aa Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:25:41 +0800 Subject: [PATCH 07/15] refactor: update mod.rs files for new category structure Co-Authored-By: Claude Opus 4.6 --- src/models/algebraic/mod.rs | 17 +++++++++++++++++ src/models/formula/mod.rs | 7 +++++-- src/models/graph/mod.rs | 10 ++++++++-- src/models/misc/mod.rs | 14 ++++++++++++++ src/models/mod.rs | 18 +++++++++--------- 5 files changed, 53 insertions(+), 13 deletions(-) create mode 100644 src/models/algebraic/mod.rs create mode 100644 src/models/misc/mod.rs diff --git a/src/models/algebraic/mod.rs b/src/models/algebraic/mod.rs new file mode 100644 index 00000000..71964f28 --- /dev/null +++ b/src/models/algebraic/mod.rs @@ -0,0 +1,17 @@ +//! Algebraic problems. +//! +//! Problems whose input is a matrix, linear system, or lattice: +//! - [`QUBO`]: Quadratic Unconstrained Binary Optimization +//! - [`ILP`]: Integer Linear Programming +//! - [`ClosestVectorProblem`]: Closest Vector Problem (minimize lattice distance) +//! - [`BMF`]: Boolean Matrix Factorization + +pub(crate) mod bmf; +mod closest_vector_problem; +mod ilp; +mod qubo; + +pub use bmf::BMF; +pub use closest_vector_problem::ClosestVectorProblem; +pub use ilp::{Comparison, LinearConstraint, ObjectiveSense, VarBounds, ILP}; +pub use qubo::QUBO; diff --git a/src/models/formula/mod.rs b/src/models/formula/mod.rs index 9766fd1c..b5a14ed2 100644 --- a/src/models/formula/mod.rs +++ b/src/models/formula/mod.rs @@ -1,11 +1,14 @@ -//! Satisfiability problems. +//! Logic and formula problems. //! -//! This module contains Boolean satisfiability problems: +//! Problems whose input is a boolean formula or circuit: //! - [`Satisfiability`]: Boolean satisfiability (SAT) with CNF clauses //! - [`KSatisfiability`]: K-SAT where each clause has exactly K literals +//! - [`CircuitSAT`]: Boolean circuit satisfiability mod ksat; mod sat; +pub(crate) mod circuit; +pub use circuit::{Assignment, BooleanExpr, BooleanOp, Circuit, CircuitSAT}; pub use ksat::KSatisfiability; pub use sat::{CNFClause, Satisfiability}; diff --git a/src/models/graph/mod.rs b/src/models/graph/mod.rs index a924af19..1198f7fb 100644 --- a/src/models/graph/mod.rs +++ b/src/models/graph/mod.rs @@ -1,6 +1,6 @@ -//! Graph-based optimization problems. +//! Graph problems. //! -//! This module contains NP-hard problems defined on graphs: +//! Problems whose input is a graph (optionally weighted): //! - [`MaximumIndependentSet`]: Maximum weight independent set //! - [`MaximalIS`]: Maximal independent set //! - [`MinimumVertexCover`]: Minimum weight vertex cover @@ -10,7 +10,10 @@ //! - [`KColoring`]: K-vertex coloring //! - [`MaximumMatching`]: Maximum weight matching //! - [`TravelingSalesman`]: Traveling Salesman (minimum weight Hamiltonian cycle) +//! - [`SpinGlass`]: Ising model Hamiltonian +//! - [`BicliqueCover`]: Biclique cover on bipartite graphs +pub(crate) mod biclique_cover; pub(crate) mod kcoloring; pub(crate) mod max_cut; pub(crate) mod maximal_is; @@ -19,8 +22,10 @@ pub(crate) mod maximum_independent_set; pub(crate) mod maximum_matching; pub(crate) mod minimum_dominating_set; pub(crate) mod minimum_vertex_cover; +pub(crate) mod spin_glass; pub(crate) mod traveling_salesman; +pub use biclique_cover::BicliqueCover; pub use kcoloring::KColoring; pub use max_cut::MaxCut; pub use maximal_is::MaximalIS; @@ -29,4 +34,5 @@ pub use maximum_independent_set::MaximumIndependentSet; pub use maximum_matching::MaximumMatching; pub use minimum_dominating_set::MinimumDominatingSet; pub use minimum_vertex_cover::MinimumVertexCover; +pub use spin_glass::SpinGlass; pub use traveling_salesman::TravelingSalesman; diff --git a/src/models/misc/mod.rs b/src/models/misc/mod.rs new file mode 100644 index 00000000..6e2fa084 --- /dev/null +++ b/src/models/misc/mod.rs @@ -0,0 +1,14 @@ +//! Miscellaneous problems. +//! +//! Problems with unique input structures that don't fit other categories: +//! - [`BinPacking`]: Bin Packing (minimize bins) +//! - [`Factoring`]: Integer factorization +//! - [`PaintShop`]: Minimize color switches in paint shop scheduling + +mod bin_packing; +pub(crate) mod factoring; +pub(crate) mod paintshop; + +pub use bin_packing::BinPacking; +pub use factoring::Factoring; +pub use paintshop::PaintShop; diff --git a/src/models/mod.rs b/src/models/mod.rs index e4671efc..fbf18ed9 100644 --- a/src/models/mod.rs +++ b/src/models/mod.rs @@ -1,19 +1,19 @@ //! Problem model implementations. //! -//! Each sub-module groups related problem types. See individual modules for details. +//! Each sub-module groups related problem types by input structure. +pub mod algebraic; +pub mod formula; pub mod graph; -pub mod optimization; -pub mod satisfiability; +pub mod misc; pub mod set; -pub mod specialized; // Re-export commonly used types +pub use algebraic::{ClosestVectorProblem, ILP, QUBO, BMF}; +pub use formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; pub use graph::{ - KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, - MinimumDominatingSet, MinimumVertexCover, TravelingSalesman, + BicliqueCover, KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, + MaximumMatching, MinimumDominatingSet, MinimumVertexCover, SpinGlass, TravelingSalesman, }; -pub use optimization::{BinPacking, ClosestVectorProblem, SpinGlass, ILP, QUBO}; -pub use satisfiability::{CNFClause, KSatisfiability, Satisfiability}; +pub use misc::{BinPacking, Factoring, PaintShop}; pub use set::{MaximumSetPacking, MinimumSetCovering}; -pub use specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; From 2b1ab2261767a6ad7bb134a5d4aa60114793db1f Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:27:04 +0800 Subject: [PATCH 08/15] refactor: move unit tests to match new category structure Co-Authored-By: Claude Opus 4.6 --- src/models/algebraic/bmf.rs | 2 +- src/models/algebraic/closest_vector_problem.rs | 2 +- src/models/algebraic/ilp.rs | 2 +- src/models/algebraic/qubo.rs | 2 +- src/models/formula/circuit.rs | 2 +- src/models/formula/ksat.rs | 2 +- src/models/formula/sat.rs | 2 +- src/models/graph/biclique_cover.rs | 2 +- src/models/graph/spin_glass.rs | 2 +- src/models/misc/bin_packing.rs | 2 +- src/models/misc/factoring.rs | 2 +- src/models/misc/paintshop.rs | 2 +- src/unit_tests/models/{specialized => algebraic}/bmf.rs | 0 .../{optimization => algebraic}/closest_vector_problem.rs | 0 src/unit_tests/models/{optimization => algebraic}/ilp.rs | 0 src/unit_tests/models/{optimization => algebraic}/qubo.rs | 0 src/unit_tests/models/{specialized => formula}/circuit.rs | 0 src/unit_tests/models/{satisfiability => formula}/ksat.rs | 0 src/unit_tests/models/{satisfiability => formula}/sat.rs | 0 src/unit_tests/models/{specialized => graph}/biclique_cover.rs | 0 src/unit_tests/models/{optimization => graph}/spin_glass.rs | 0 src/unit_tests/models/{optimization => misc}/bin_packing.rs | 0 src/unit_tests/models/{specialized => misc}/factoring.rs | 0 src/unit_tests/models/{specialized => misc}/paintshop.rs | 0 24 files changed, 12 insertions(+), 12 deletions(-) rename src/unit_tests/models/{specialized => algebraic}/bmf.rs (100%) rename src/unit_tests/models/{optimization => algebraic}/closest_vector_problem.rs (100%) rename src/unit_tests/models/{optimization => algebraic}/ilp.rs (100%) rename src/unit_tests/models/{optimization => algebraic}/qubo.rs (100%) rename src/unit_tests/models/{specialized => formula}/circuit.rs (100%) rename src/unit_tests/models/{satisfiability => formula}/ksat.rs (100%) rename src/unit_tests/models/{satisfiability => formula}/sat.rs (100%) rename src/unit_tests/models/{specialized => graph}/biclique_cover.rs (100%) rename src/unit_tests/models/{optimization => graph}/spin_glass.rs (100%) rename src/unit_tests/models/{optimization => misc}/bin_packing.rs (100%) rename src/unit_tests/models/{specialized => misc}/factoring.rs (100%) rename src/unit_tests/models/{specialized => misc}/paintshop.rs (100%) diff --git a/src/models/algebraic/bmf.rs b/src/models/algebraic/bmf.rs index a7426044..fcccb5d3 100644 --- a/src/models/algebraic/bmf.rs +++ b/src/models/algebraic/bmf.rs @@ -235,5 +235,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/specialized/bmf.rs"] +#[path = "../../unit_tests/models/algebraic/bmf.rs"] mod tests; diff --git a/src/models/algebraic/closest_vector_problem.rs b/src/models/algebraic/closest_vector_problem.rs index e8883cd6..94a0a30b 100644 --- a/src/models/algebraic/closest_vector_problem.rs +++ b/src/models/algebraic/closest_vector_problem.rs @@ -178,5 +178,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/optimization/closest_vector_problem.rs"] +#[path = "../../unit_tests/models/algebraic/closest_vector_problem.rs"] mod tests; diff --git a/src/models/algebraic/ilp.rs b/src/models/algebraic/ilp.rs index cd538789..9d7624a5 100644 --- a/src/models/algebraic/ilp.rs +++ b/src/models/algebraic/ilp.rs @@ -381,5 +381,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/optimization/ilp.rs"] +#[path = "../../unit_tests/models/algebraic/ilp.rs"] mod tests; diff --git a/src/models/algebraic/qubo.rs b/src/models/algebraic/qubo.rs index 21107188..9553888d 100644 --- a/src/models/algebraic/qubo.rs +++ b/src/models/algebraic/qubo.rs @@ -193,5 +193,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/optimization/qubo.rs"] +#[path = "../../unit_tests/models/algebraic/qubo.rs"] mod tests; diff --git a/src/models/formula/circuit.rs b/src/models/formula/circuit.rs index 024fd1b4..55e9e803 100644 --- a/src/models/formula/circuit.rs +++ b/src/models/formula/circuit.rs @@ -309,5 +309,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/specialized/circuit.rs"] +#[path = "../../unit_tests/models/formula/circuit.rs"] mod tests; diff --git a/src/models/formula/ksat.rs b/src/models/formula/ksat.rs index f2f0a1ac..67983ddc 100644 --- a/src/models/formula/ksat.rs +++ b/src/models/formula/ksat.rs @@ -190,5 +190,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/satisfiability/ksat.rs"] +#[path = "../../unit_tests/models/formula/ksat.rs"] mod tests; diff --git a/src/models/formula/sat.rs b/src/models/formula/sat.rs index 4401008b..080822b8 100644 --- a/src/models/formula/sat.rs +++ b/src/models/formula/sat.rs @@ -225,5 +225,5 @@ pub(crate) fn is_satisfying_assignment( } #[cfg(test)] -#[path = "../../unit_tests/models/satisfiability/sat.rs"] +#[path = "../../unit_tests/models/formula/sat.rs"] mod tests; diff --git a/src/models/graph/biclique_cover.rs b/src/models/graph/biclique_cover.rs index 078c75b4..e29c6406 100644 --- a/src/models/graph/biclique_cover.rs +++ b/src/models/graph/biclique_cover.rs @@ -248,5 +248,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/specialized/biclique_cover.rs"] +#[path = "../../unit_tests/models/graph/biclique_cover.rs"] mod tests; diff --git a/src/models/graph/spin_glass.rs b/src/models/graph/spin_glass.rs index abeedb4c..136fda44 100644 --- a/src/models/graph/spin_glass.rs +++ b/src/models/graph/spin_glass.rs @@ -256,5 +256,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/optimization/spin_glass.rs"] +#[path = "../../unit_tests/models/graph/spin_glass.rs"] mod tests; diff --git a/src/models/misc/bin_packing.rs b/src/models/misc/bin_packing.rs index 1641ee77..45d5c1c5 100644 --- a/src/models/misc/bin_packing.rs +++ b/src/models/misc/bin_packing.rs @@ -156,5 +156,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/optimization/bin_packing.rs"] +#[path = "../../unit_tests/models/misc/bin_packing.rs"] mod tests; diff --git a/src/models/misc/factoring.rs b/src/models/misc/factoring.rs index 66de6907..7d7524fd 100644 --- a/src/models/misc/factoring.rs +++ b/src/models/misc/factoring.rs @@ -167,5 +167,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/specialized/factoring.rs"] +#[path = "../../unit_tests/models/misc/factoring.rs"] mod tests; diff --git a/src/models/misc/paintshop.rs b/src/models/misc/paintshop.rs index 2d21df3a..b83ba407 100644 --- a/src/models/misc/paintshop.rs +++ b/src/models/misc/paintshop.rs @@ -197,5 +197,5 @@ crate::declare_variants! { } #[cfg(test)] -#[path = "../../unit_tests/models/specialized/paintshop.rs"] +#[path = "../../unit_tests/models/misc/paintshop.rs"] mod tests; diff --git a/src/unit_tests/models/specialized/bmf.rs b/src/unit_tests/models/algebraic/bmf.rs similarity index 100% rename from src/unit_tests/models/specialized/bmf.rs rename to src/unit_tests/models/algebraic/bmf.rs diff --git a/src/unit_tests/models/optimization/closest_vector_problem.rs b/src/unit_tests/models/algebraic/closest_vector_problem.rs similarity index 100% rename from src/unit_tests/models/optimization/closest_vector_problem.rs rename to src/unit_tests/models/algebraic/closest_vector_problem.rs diff --git a/src/unit_tests/models/optimization/ilp.rs b/src/unit_tests/models/algebraic/ilp.rs similarity index 100% rename from src/unit_tests/models/optimization/ilp.rs rename to src/unit_tests/models/algebraic/ilp.rs diff --git a/src/unit_tests/models/optimization/qubo.rs b/src/unit_tests/models/algebraic/qubo.rs similarity index 100% rename from src/unit_tests/models/optimization/qubo.rs rename to src/unit_tests/models/algebraic/qubo.rs diff --git a/src/unit_tests/models/specialized/circuit.rs b/src/unit_tests/models/formula/circuit.rs similarity index 100% rename from src/unit_tests/models/specialized/circuit.rs rename to src/unit_tests/models/formula/circuit.rs diff --git a/src/unit_tests/models/satisfiability/ksat.rs b/src/unit_tests/models/formula/ksat.rs similarity index 100% rename from src/unit_tests/models/satisfiability/ksat.rs rename to src/unit_tests/models/formula/ksat.rs diff --git a/src/unit_tests/models/satisfiability/sat.rs b/src/unit_tests/models/formula/sat.rs similarity index 100% rename from src/unit_tests/models/satisfiability/sat.rs rename to src/unit_tests/models/formula/sat.rs diff --git a/src/unit_tests/models/specialized/biclique_cover.rs b/src/unit_tests/models/graph/biclique_cover.rs similarity index 100% rename from src/unit_tests/models/specialized/biclique_cover.rs rename to src/unit_tests/models/graph/biclique_cover.rs diff --git a/src/unit_tests/models/optimization/spin_glass.rs b/src/unit_tests/models/graph/spin_glass.rs similarity index 100% rename from src/unit_tests/models/optimization/spin_glass.rs rename to src/unit_tests/models/graph/spin_glass.rs diff --git a/src/unit_tests/models/optimization/bin_packing.rs b/src/unit_tests/models/misc/bin_packing.rs similarity index 100% rename from src/unit_tests/models/optimization/bin_packing.rs rename to src/unit_tests/models/misc/bin_packing.rs diff --git a/src/unit_tests/models/specialized/factoring.rs b/src/unit_tests/models/misc/factoring.rs similarity index 100% rename from src/unit_tests/models/specialized/factoring.rs rename to src/unit_tests/models/misc/factoring.rs diff --git a/src/unit_tests/models/specialized/paintshop.rs b/src/unit_tests/models/misc/paintshop.rs similarity index 100% rename from src/unit_tests/models/specialized/paintshop.rs rename to src/unit_tests/models/misc/paintshop.rs From d24d0fb66195b69df748b586e8cb88490499e746 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:28:52 +0800 Subject: [PATCH 09/15] refactor: update rule imports for new model categories Co-Authored-By: Claude Opus 4.6 --- src/rules/circuit_ilp.rs | 4 ++-- src/rules/circuit_spinglass.rs | 4 ++-- src/rules/coloring_ilp.rs | 2 +- src/rules/coloring_qubo.rs | 2 +- src/rules/factoring_circuit.rs | 3 ++- src/rules/factoring_ilp.rs | 4 ++-- src/rules/ilp_qubo.rs | 2 +- src/rules/ksatisfiability_casts.rs | 2 +- src/rules/ksatisfiability_qubo.rs | 6 +++--- src/rules/maximumclique_ilp.rs | 2 +- src/rules/maximumindependentset_ilp.rs | 2 +- src/rules/maximumindependentset_qubo.rs | 2 +- src/rules/maximummatching_ilp.rs | 2 +- src/rules/maximumsetpacking_ilp.rs | 2 +- src/rules/maximumsetpacking_qubo.rs | 2 +- src/rules/minimumdominatingset_ilp.rs | 2 +- src/rules/minimumsetcovering_ilp.rs | 2 +- src/rules/minimumvertexcover_ilp.rs | 2 +- src/rules/minimumvertexcover_qubo.rs | 2 +- src/rules/qubo_ilp.rs | 2 +- src/rules/sat_circuitsat.rs | 4 ++-- src/rules/sat_coloring.rs | 2 +- src/rules/sat_ksat.rs | 2 +- src/rules/sat_maximumindependentset.rs | 2 +- src/rules/sat_minimumdominatingset.rs | 2 +- src/rules/spinglass_casts.rs | 2 +- src/rules/spinglass_maxcut.rs | 2 +- src/rules/spinglass_qubo.rs | 3 ++- src/rules/travelingsalesman_ilp.rs | 2 +- 29 files changed, 37 insertions(+), 35 deletions(-) diff --git a/src/rules/circuit_ilp.rs b/src/rules/circuit_ilp.rs index 67e85ea4..6befb2bb 100644 --- a/src/rules/circuit_ilp.rs +++ b/src/rules/circuit_ilp.rs @@ -14,8 +14,8 @@ //! ## Objective //! Trivial (minimize 0): any feasible ILP solution is a satisfying assignment. -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; -use crate::models::specialized::{BooleanExpr, BooleanOp, CircuitSAT}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::formula::{BooleanExpr, BooleanOp, CircuitSAT}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use std::collections::HashMap; diff --git a/src/rules/circuit_spinglass.rs b/src/rules/circuit_spinglass.rs index e002fd26..8c392aeb 100644 --- a/src/rules/circuit_spinglass.rs +++ b/src/rules/circuit_spinglass.rs @@ -6,8 +6,8 @@ //! Each logic gate is encoded as a SpinGlass Hamiltonian where the ground //! states correspond to valid input/output combinations. -use crate::models::optimization::SpinGlass; -use crate::models::specialized::{Assignment, BooleanExpr, BooleanOp, CircuitSAT}; +use crate::models::graph::SpinGlass; +use crate::models::formula::{Assignment, BooleanExpr, BooleanOp, CircuitSAT}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::SimpleGraph; diff --git a/src/rules/coloring_ilp.rs b/src/rules/coloring_ilp.rs index b80dad20..eb93af77 100644 --- a/src/rules/coloring_ilp.rs +++ b/src/rules/coloring_ilp.rs @@ -8,7 +8,7 @@ //! - Objective: None (feasibility problem, minimize 0) use crate::models::graph::KColoring; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/coloring_qubo.rs b/src/rules/coloring_qubo.rs index 5f1573c6..c5062baf 100644 --- a/src/rules/coloring_qubo.rs +++ b/src/rules/coloring_qubo.rs @@ -9,7 +9,7 @@ //! QUBO has n*K variables. use crate::models::graph::KColoring; -use crate::models::optimization::QUBO; +use crate::models::algebraic::QUBO; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/factoring_circuit.rs b/src/rules/factoring_circuit.rs index 3160d7c3..1400a032 100644 --- a/src/rules/factoring_circuit.rs +++ b/src/rules/factoring_circuit.rs @@ -7,7 +7,8 @@ //! The multiplier circuit uses an array multiplier structure with //! carry propagation, building up partial products row by row. -use crate::models::specialized::{Assignment, BooleanExpr, Circuit, CircuitSAT, Factoring}; +use crate::models::formula::{Assignment, BooleanExpr, Circuit, CircuitSAT}; +use crate::models::misc::Factoring; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; /// Result of reducing Factoring to CircuitSAT. diff --git a/src/rules/factoring_ilp.rs b/src/rules/factoring_ilp.rs index 3cb0045d..e2724cc1 100644 --- a/src/rules/factoring_ilp.rs +++ b/src/rules/factoring_ilp.rs @@ -17,8 +17,8 @@ //! 2. Bit-position sums: Σ_{i+j=k} z_ij + c_{k-1} = N_k + 2·c_k //! 3. No overflow: c_{m+n-1} = 0 -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; -use crate::models::specialized::Factoring; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::misc::Factoring; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use std::cmp::min; diff --git a/src/rules/ilp_qubo.rs b/src/rules/ilp_qubo.rs index 6f2c7d6b..ab901a44 100644 --- a/src/rules/ilp_qubo.rs +++ b/src/rules/ilp_qubo.rs @@ -9,7 +9,7 @@ //! For Minimize sense, c is negated (convert to maximization). //! Slack variables: ceil(log2(slack_range)) bits per inequality constraint. -use crate::models::optimization::{Comparison, ObjectiveSense, ILP, QUBO}; +use crate::models::algebraic::{Comparison, ObjectiveSense, ILP, QUBO}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/ksatisfiability_casts.rs b/src/rules/ksatisfiability_casts.rs index 1f2857ff..e98a02a1 100644 --- a/src/rules/ksatisfiability_casts.rs +++ b/src/rules/ksatisfiability_casts.rs @@ -1,7 +1,7 @@ //! Variant cast reductions for KSatisfiability. use crate::impl_variant_reduction; -use crate::models::satisfiability::KSatisfiability; +use crate::models::formula::KSatisfiability; use crate::variant::{K2, K3, KN}; impl_variant_reduction!( diff --git a/src/rules/ksatisfiability_qubo.rs b/src/rules/ksatisfiability_qubo.rs index cbf60226..7bf640da 100644 --- a/src/rules/ksatisfiability_qubo.rs +++ b/src/rules/ksatisfiability_qubo.rs @@ -12,8 +12,8 @@ //! //! CNFClause uses 1-indexed signed integers: positive = variable, negative = negated. -use crate::models::optimization::QUBO; -use crate::models::satisfiability::KSatisfiability; +use crate::models::algebraic::QUBO; +use crate::models::formula::KSatisfiability; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::variant::{K2, K3}; @@ -265,7 +265,7 @@ fn add_3sat_clause_penalty(matrix: &mut [Vec], lits: &[i32], aux_var: usize /// Returns (matrix, num_source_vars) where matrix is (n + aux) x (n + aux). fn build_qubo_matrix( num_vars: usize, - clauses: &[crate::models::satisfiability::CNFClause], + clauses: &[crate::models::formula::CNFClause], k: usize, ) -> Vec> { match k { diff --git a/src/rules/maximumclique_ilp.rs b/src/rules/maximumclique_ilp.rs index 2bcd87d3..4d968009 100644 --- a/src/rules/maximumclique_ilp.rs +++ b/src/rules/maximumclique_ilp.rs @@ -7,7 +7,7 @@ //! - Objective: Maximize the sum of weights of selected vertices use crate::models::graph::MaximumClique; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximumindependentset_ilp.rs b/src/rules/maximumindependentset_ilp.rs index 5396c396..7313afea 100644 --- a/src/rules/maximumindependentset_ilp.rs +++ b/src/rules/maximumindependentset_ilp.rs @@ -6,7 +6,7 @@ //! - Objective: Maximize the sum of weights of selected vertices use crate::models::graph::MaximumIndependentSet; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximumindependentset_qubo.rs b/src/rules/maximumindependentset_qubo.rs index 9dd32a07..fe3a4592 100644 --- a/src/rules/maximumindependentset_qubo.rs +++ b/src/rules/maximumindependentset_qubo.rs @@ -6,7 +6,7 @@ //! Q[i][i] = -w_i, Q[i][j] = P for edges. P = 1 + Σ w_i. use crate::models::graph::MaximumIndependentSet; -use crate::models::optimization::QUBO; +use crate::models::algebraic::QUBO; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximummatching_ilp.rs b/src/rules/maximummatching_ilp.rs index 681e0092..aa19cda5 100644 --- a/src/rules/maximummatching_ilp.rs +++ b/src/rules/maximummatching_ilp.rs @@ -7,7 +7,7 @@ //! - Objective: Maximize the sum of weights of selected edges use crate::models::graph::MaximumMatching; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximumsetpacking_ilp.rs b/src/rules/maximumsetpacking_ilp.rs index 13f61071..cd2d7093 100644 --- a/src/rules/maximumsetpacking_ilp.rs +++ b/src/rules/maximumsetpacking_ilp.rs @@ -5,7 +5,7 @@ //! - Constraints: x_i + x_j <= 1 for each overlapping pair (i, j) //! - Objective: Maximize the sum of weights of selected sets -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::models::set::MaximumSetPacking; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/maximumsetpacking_qubo.rs b/src/rules/maximumsetpacking_qubo.rs index 9fdce7ee..7ccbf781 100644 --- a/src/rules/maximumsetpacking_qubo.rs +++ b/src/rules/maximumsetpacking_qubo.rs @@ -6,7 +6,7 @@ //! //! Q[i][i] = -w_i, Q[i][j] = P for overlapping pairs. P = 1 + Σ w_i. -use crate::models::optimization::QUBO; +use crate::models::algebraic::QUBO; use crate::models::set::MaximumSetPacking; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/minimumdominatingset_ilp.rs b/src/rules/minimumdominatingset_ilp.rs index abce597b..ce246e92 100644 --- a/src/rules/minimumdominatingset_ilp.rs +++ b/src/rules/minimumdominatingset_ilp.rs @@ -7,7 +7,7 @@ //! - Objective: Minimize the sum of weights of selected vertices use crate::models::graph::MinimumDominatingSet; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/minimumsetcovering_ilp.rs b/src/rules/minimumsetcovering_ilp.rs index 4f4bb6c5..ced7991d 100644 --- a/src/rules/minimumsetcovering_ilp.rs +++ b/src/rules/minimumsetcovering_ilp.rs @@ -5,7 +5,7 @@ //! - Constraints: For each element e: sum_{j: e in set_j} x_j >= 1 (element must be covered) //! - Objective: Minimize the sum of weights of selected sets -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::models::set::MinimumSetCovering; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/minimumvertexcover_ilp.rs b/src/rules/minimumvertexcover_ilp.rs index 9f076bd8..dea767a3 100644 --- a/src/rules/minimumvertexcover_ilp.rs +++ b/src/rules/minimumvertexcover_ilp.rs @@ -6,7 +6,7 @@ //! - Objective: Minimize the sum of weights of selected vertices use crate::models::graph::MinimumVertexCover; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/minimumvertexcover_qubo.rs b/src/rules/minimumvertexcover_qubo.rs index e484c724..99c38d0b 100644 --- a/src/rules/minimumvertexcover_qubo.rs +++ b/src/rules/minimumvertexcover_qubo.rs @@ -7,7 +7,7 @@ //! P = 1 + Σ w_i. use crate::models::graph::MinimumVertexCover; -use crate::models::optimization::QUBO; +use crate::models::algebraic::QUBO; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/qubo_ilp.rs b/src/rules/qubo_ilp.rs index 89d14f94..07a38226 100644 --- a/src/rules/qubo_ilp.rs +++ b/src/rules/qubo_ilp.rs @@ -14,7 +14,7 @@ //! ## Objective //! minimize Σ_i Q_ii · x_i + Σ_{i SAT: Trivial embedding (K-SAT is a special case of SAT) -use crate::models::satisfiability::{CNFClause, KSatisfiability, Satisfiability}; +use crate::models::formula::{CNFClause, KSatisfiability, Satisfiability}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::variant::{KValue, K2, K3, KN}; diff --git a/src/rules/sat_maximumindependentset.rs b/src/rules/sat_maximumindependentset.rs index f39afe72..b601b792 100644 --- a/src/rules/sat_maximumindependentset.rs +++ b/src/rules/sat_maximumindependentset.rs @@ -9,7 +9,7 @@ //! where we pick exactly one literal from each clause. use crate::models::graph::MaximumIndependentSet; -use crate::models::satisfiability::Satisfiability; +use crate::models::formula::Satisfiability; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::SimpleGraph; diff --git a/src/rules/sat_minimumdominatingset.rs b/src/rules/sat_minimumdominatingset.rs index 7dd1570f..a4cb80a6 100644 --- a/src/rules/sat_minimumdominatingset.rs +++ b/src/rules/sat_minimumdominatingset.rs @@ -15,7 +15,7 @@ //! - Selecting the dummy vertex means the variable can be either (unused in any clause) use crate::models::graph::MinimumDominatingSet; -use crate::models::satisfiability::Satisfiability; +use crate::models::formula::Satisfiability; use crate::reduction; use crate::rules::sat_maximumindependentset::BoolVar; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/spinglass_casts.rs b/src/rules/spinglass_casts.rs index 50868094..81693c23 100644 --- a/src/rules/spinglass_casts.rs +++ b/src/rules/spinglass_casts.rs @@ -1,7 +1,7 @@ //! Variant cast reductions for SpinGlass. use crate::impl_variant_reduction; -use crate::models::optimization::SpinGlass; +use crate::models::graph::SpinGlass; use crate::topology::SimpleGraph; use crate::variant::CastToParent; diff --git a/src/rules/spinglass_maxcut.rs b/src/rules/spinglass_maxcut.rs index 813480eb..75ca9df8 100644 --- a/src/rules/spinglass_maxcut.rs +++ b/src/rules/spinglass_maxcut.rs @@ -4,7 +4,7 @@ //! SpinGlass -> MaxCut: Requires ancilla vertex for onsite terms. use crate::models::graph::MaxCut; -use crate::models::optimization::SpinGlass; +use crate::models::graph::SpinGlass; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/spinglass_qubo.rs b/src/rules/spinglass_qubo.rs index 178c9481..d6b441b5 100644 --- a/src/rules/spinglass_qubo.rs +++ b/src/rules/spinglass_qubo.rs @@ -5,7 +5,8 @@ //! //! Transformation: s = 2x - 1 (so x=0 -> s=-1, x=1 -> s=+1) -use crate::models::optimization::{SpinGlass, QUBO}; +use crate::models::algebraic::QUBO; +use crate::models::graph::SpinGlass; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::SimpleGraph; diff --git a/src/rules/travelingsalesman_ilp.rs b/src/rules/travelingsalesman_ilp.rs index a5a331ca..d00e48c5 100644 --- a/src/rules/travelingsalesman_ilp.rs +++ b/src/rules/travelingsalesman_ilp.rs @@ -6,7 +6,7 @@ //! - Objective: minimize total edge weight of the tour use crate::models::graph::TravelingSalesman; -use crate::models::optimization::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; From f3354252219078f9e559c4239a2eb72cc69e7132 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:29:34 +0800 Subject: [PATCH 10/15] refactor: update lib.rs prelude and docs for new categories Co-Authored-By: Claude Opus 4.6 --- src/lib.rs | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/lib.rs b/src/lib.rs index 33ca9c45..15e10d49 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -7,7 +7,7 @@ //! //! | Module | Purpose | //! |--------|---------| -//! | [`models`] | Problem types — [`graph`](models::graph), [`satisfiability`](models::satisfiability), [`set`](models::set), [`optimization`](models::optimization), [`specialized`](models::specialized) | +//! | [`models`] | Problem types — [`graph`](models::graph), [`formula`](models::formula), [`set`](models::set), [`algebraic`](models::algebraic), [`misc`](models::misc) | //! | [`rules`] | Reduction rules, [`ReductionGraph`](rules::ReductionGraph) for path search | //! | [`solvers`] | [`BruteForce`] and [`ILPSolver`](solvers::ILPSolver) | //! | [`topology`] | Graph types — [`SimpleGraph`](topology::SimpleGraph), [`HyperGraph`](topology::HyperGraph), [`UnitDiskGraph`](topology::UnitDiskGraph), etc. | @@ -40,10 +40,11 @@ pub mod prelude { KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, MinimumDominatingSet, MinimumVertexCover, TravelingSalesman, }; - pub use crate::models::optimization::{SpinGlass, QUBO}; - pub use crate::models::satisfiability::{CNFClause, KSatisfiability, Satisfiability}; + pub use crate::models::algebraic::{QUBO, BMF}; + pub use crate::models::formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; + pub use crate::models::graph::{BicliqueCover, SpinGlass}; + pub use crate::models::misc::{BinPacking, Factoring, PaintShop}; pub use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; - pub use crate::models::specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; // Core traits pub use crate::rules::{ReduceTo, ReductionResult}; From 68d2d48404d99a3933b633cc1fd5254b552ef3c3 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:47:33 +0800 Subject: [PATCH 11/15] refactor: update all imports, tests, examples, and docs for new categories Updates imports across unit tests, integration tests, examples, benchmarks, CLI, solver, and source doc comments from old categories (optimization, satisfiability, specialized) to new ones (algebraic, formula, graph, misc). Co-Authored-By: Claude Opus 4.6 --- benches/solver_benchmarks.rs | 5 +- examples/reduction_circuitsat_to_ilp.rs | 4 +- examples/reduction_circuitsat_to_spinglass.rs | 2 +- examples/reduction_factoring_to_circuitsat.rs | 2 +- examples/reduction_factoring_to_ilp.rs | 2 +- examples/reduction_ilp_to_qubo.rs | 2 +- examples/reduction_kcoloring_to_ilp.rs | 2 +- examples/reduction_maximumclique_to_ilp.rs | 2 +- .../reduction_maximumindependentset_to_ilp.rs | 2 +- examples/reduction_maximummatching_to_ilp.rs | 2 +- .../reduction_maximumsetpacking_to_ilp.rs | 2 +- .../reduction_minimumdominatingset_to_ilp.rs | 2 +- .../reduction_minimumsetcovering_to_ilp.rs | 2 +- .../reduction_minimumvertexcover_to_ilp.rs | 2 +- examples/reduction_qubo_to_ilp.rs | 2 +- .../reduction_travelingsalesman_to_ilp.rs | 2 +- problemreductions-cli/src/dispatch.rs | 3 +- problemreductions-cli/src/mcp/tools.rs | 7 ++- src/models/algebraic/bmf.rs | 2 +- .../algebraic/closest_vector_problem.rs | 2 +- src/models/algebraic/ilp.rs | 2 +- src/models/algebraic/qubo.rs | 2 +- src/models/formula/circuit.rs | 2 +- src/models/formula/ksat.rs | 2 +- src/models/formula/sat.rs | 2 +- src/models/graph/biclique_cover.rs | 2 +- src/models/graph/spin_glass.rs | 2 +- src/models/misc/bin_packing.rs | 2 +- src/models/misc/factoring.rs | 2 +- src/models/misc/paintshop.rs | 2 +- src/solvers/ilp/mod.rs | 2 +- src/solvers/ilp/solver.rs | 4 +- src/unit_tests/jl_helpers.rs | 4 +- src/unit_tests/problem_size.rs | 14 ++--- src/unit_tests/reduction_graph.rs | 6 +- src/unit_tests/rules/circuit_ilp.rs | 2 +- src/unit_tests/rules/circuit_spinglass.rs | 4 +- src/unit_tests/rules/graph.rs | 60 ++++++++++--------- src/unit_tests/rules/ilp_qubo.rs | 2 +- src/unit_tests/rules/ksatisfiability_qubo.rs | 2 +- src/unit_tests/rules/reduction_path_parity.rs | 6 +- src/unit_tests/rules/registry.rs | 4 +- src/unit_tests/rules/sat_circuitsat.rs | 3 +- src/unit_tests/rules/sat_coloring.rs | 2 +- .../rules/sat_maximumindependentset.rs | 2 +- .../rules/sat_minimumdominatingset.rs | 2 +- src/unit_tests/solvers/brute_force.rs | 2 +- src/unit_tests/solvers/ilp/solver.rs | 2 +- src/unit_tests/trait_consistency.rs | 6 +- .../unitdiskmapping_algorithms/common.rs | 2 +- .../unitdiskmapping_algorithms/weighted.rs | 2 +- src/unit_tests/variant.rs | 7 ++- tests/suites/integration.rs | 6 +- tests/suites/reductions.rs | 2 +- 54 files changed, 111 insertions(+), 108 deletions(-) diff --git a/benches/solver_benchmarks.rs b/benches/solver_benchmarks.rs index c77d7bbf..0ee082fc 100644 --- a/benches/solver_benchmarks.rs +++ b/benches/solver_benchmarks.rs @@ -1,11 +1,10 @@ //! Benchmarks for the BruteForce solver on various problem types. use criterion::{criterion_group, criterion_main, BenchmarkId, Criterion}; +use problemreductions::models::formula::*; use problemreductions::models::graph::*; -use problemreductions::models::optimization::*; -use problemreductions::models::satisfiability::*; +use problemreductions::models::misc::*; use problemreductions::models::set::*; -use problemreductions::models::specialized::*; use problemreductions::prelude::*; use problemreductions::topology::SimpleGraph; use problemreductions::variant::K3; diff --git a/examples/reduction_circuitsat_to_ilp.rs b/examples/reduction_circuitsat_to_ilp.rs index a5415087..4bbc42d4 100644 --- a/examples/reduction_circuitsat_to_ilp.rs +++ b/examples/reduction_circuitsat_to_ilp.rs @@ -23,8 +23,8 @@ // ``` use problemreductions::export::*; -use problemreductions::models::optimization::ILP; -use problemreductions::models::specialized::{Assignment, BooleanExpr, Circuit}; +use problemreductions::models::algebraic::ILP; +use problemreductions::models::formula::{Assignment, BooleanExpr, Circuit}; use problemreductions::prelude::*; pub fn run() { diff --git a/examples/reduction_circuitsat_to_spinglass.rs b/examples/reduction_circuitsat_to_spinglass.rs index 9e9675d4..7d986cd0 100644 --- a/examples/reduction_circuitsat_to_spinglass.rs +++ b/examples/reduction_circuitsat_to_spinglass.rs @@ -17,7 +17,7 @@ // Exports `docs/paper/examples/circuitsat_to_spinglass.json` and `circuitsat_to_spinglass.result.json`. use problemreductions::export::*; -use problemreductions::models::specialized::{Assignment, BooleanExpr, Circuit}; +use problemreductions::models::formula::{Assignment, BooleanExpr, Circuit}; use problemreductions::prelude::*; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/examples/reduction_factoring_to_circuitsat.rs b/examples/reduction_factoring_to_circuitsat.rs index 22a3651c..7083d46c 100644 --- a/examples/reduction_factoring_to_circuitsat.rs +++ b/examples/reduction_factoring_to_circuitsat.rs @@ -19,7 +19,7 @@ // Exports `docs/paper/examples/factoring_to_circuitsat.json` and `factoring_to_circuitsat.result.json`. use problemreductions::export::*; -use problemreductions::models::specialized::Circuit; +use problemreductions::models::formula::Circuit; use problemreductions::prelude::*; use std::collections::HashMap; diff --git a/examples/reduction_factoring_to_ilp.rs b/examples/reduction_factoring_to_ilp.rs index a9bf1fc0..1f0013ab 100644 --- a/examples/reduction_factoring_to_ilp.rs +++ b/examples/reduction_factoring_to_ilp.rs @@ -18,7 +18,7 @@ // Exports `docs/paper/examples/factoring_to_ilp.json` for use in paper code blocks. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::solvers::ILPSolver; diff --git a/examples/reduction_ilp_to_qubo.rs b/examples/reduction_ilp_to_qubo.rs index 2c2ff115..804cef94 100644 --- a/examples/reduction_ilp_to_qubo.rs +++ b/examples/reduction_ilp_to_qubo.rs @@ -36,7 +36,7 @@ // ``` use problemreductions::export::*; -use problemreductions::models::optimization::{LinearConstraint, ObjectiveSense, ILP}; +use problemreductions::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}; use problemreductions::prelude::*; pub fn run() { diff --git a/examples/reduction_kcoloring_to_ilp.rs b/examples/reduction_kcoloring_to_ilp.rs index b52fac60..d287f0aa 100644 --- a/examples/reduction_kcoloring_to_ilp.rs +++ b/examples/reduction_kcoloring_to_ilp.rs @@ -16,7 +16,7 @@ // Exports `docs/paper/examples/kcoloring_to_ilp.json` and `kcoloring_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::solvers::ILPSolver; use problemreductions::topology::small_graphs::petersen; diff --git a/examples/reduction_maximumclique_to_ilp.rs b/examples/reduction_maximumclique_to_ilp.rs index 978eddc2..1785c242 100644 --- a/examples/reduction_maximumclique_to_ilp.rs +++ b/examples/reduction_maximumclique_to_ilp.rs @@ -15,7 +15,7 @@ // Exports `docs/paper/examples/maximumclique_to_ilp.json` and `maximumclique_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::topology::small_graphs::octahedral; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/examples/reduction_maximumindependentset_to_ilp.rs b/examples/reduction_maximumindependentset_to_ilp.rs index babac97a..cb66e151 100644 --- a/examples/reduction_maximumindependentset_to_ilp.rs +++ b/examples/reduction_maximumindependentset_to_ilp.rs @@ -14,7 +14,7 @@ // Exports `docs/paper/examples/maximumindependentset_to_ilp.json` and `maximumindependentset_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::topology::small_graphs::petersen; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/examples/reduction_maximummatching_to_ilp.rs b/examples/reduction_maximummatching_to_ilp.rs index 2c6ca348..ec482e64 100644 --- a/examples/reduction_maximummatching_to_ilp.rs +++ b/examples/reduction_maximummatching_to_ilp.rs @@ -14,7 +14,7 @@ // Exports `docs/paper/examples/maximummatching_to_ilp.json` and `maximummatching_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::topology::small_graphs::petersen; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/examples/reduction_maximumsetpacking_to_ilp.rs b/examples/reduction_maximumsetpacking_to_ilp.rs index 5e6ce4b7..86faf44e 100644 --- a/examples/reduction_maximumsetpacking_to_ilp.rs +++ b/examples/reduction_maximumsetpacking_to_ilp.rs @@ -15,7 +15,7 @@ // Exports `docs/paper/examples/maximumsetpacking_to_ilp.json` and `maximumsetpacking_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; pub fn run() { diff --git a/examples/reduction_minimumdominatingset_to_ilp.rs b/examples/reduction_minimumdominatingset_to_ilp.rs index 57aa18e6..959ec4e3 100644 --- a/examples/reduction_minimumdominatingset_to_ilp.rs +++ b/examples/reduction_minimumdominatingset_to_ilp.rs @@ -14,7 +14,7 @@ // Exports `docs/paper/examples/minimumdominatingset_to_ilp.json` and `minimumdominatingset_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::topology::small_graphs::petersen; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/examples/reduction_minimumsetcovering_to_ilp.rs b/examples/reduction_minimumsetcovering_to_ilp.rs index f7b28fa2..ba514c62 100644 --- a/examples/reduction_minimumsetcovering_to_ilp.rs +++ b/examples/reduction_minimumsetcovering_to_ilp.rs @@ -15,7 +15,7 @@ // Exports `docs/paper/examples/minimumsetcovering_to_ilp.json` and `minimumsetcovering_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; pub fn run() { diff --git a/examples/reduction_minimumvertexcover_to_ilp.rs b/examples/reduction_minimumvertexcover_to_ilp.rs index af6a212e..6e674008 100644 --- a/examples/reduction_minimumvertexcover_to_ilp.rs +++ b/examples/reduction_minimumvertexcover_to_ilp.rs @@ -14,7 +14,7 @@ // Exports `docs/paper/examples/minimumvertexcover_to_ilp.json` and `minimumvertexcover_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::topology::small_graphs::petersen; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/examples/reduction_qubo_to_ilp.rs b/examples/reduction_qubo_to_ilp.rs index 2dcaaa86..0ab13ced 100644 --- a/examples/reduction_qubo_to_ilp.rs +++ b/examples/reduction_qubo_to_ilp.rs @@ -26,7 +26,7 @@ // ``` use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; pub fn run() { diff --git a/examples/reduction_travelingsalesman_to_ilp.rs b/examples/reduction_travelingsalesman_to_ilp.rs index 28b629ba..b0ce59bf 100644 --- a/examples/reduction_travelingsalesman_to_ilp.rs +++ b/examples/reduction_travelingsalesman_to_ilp.rs @@ -15,7 +15,7 @@ // Exports `docs/paper/examples/travelingsalesman_to_ilp.json` and `travelingsalesman_to_ilp.result.json`. use problemreductions::export::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::prelude::*; use problemreductions::solvers::ILPSolver; use problemreductions::topology::{Graph, SimpleGraph}; diff --git a/problemreductions-cli/src/dispatch.rs b/problemreductions-cli/src/dispatch.rs index 877ffb2d..a6b0011f 100644 --- a/problemreductions-cli/src/dispatch.rs +++ b/problemreductions-cli/src/dispatch.rs @@ -1,5 +1,6 @@ use anyhow::{bail, Context, Result}; -use problemreductions::models::optimization::{BinPacking, ClosestVectorProblem, ILP}; +use problemreductions::models::algebraic::{ClosestVectorProblem, ILP}; +use problemreductions::models::misc::BinPacking; use problemreductions::prelude::*; use problemreductions::rules::{MinimizeSteps, ReductionGraph}; use problemreductions::solvers::{BruteForce, ILPSolver, Solver}; diff --git a/problemreductions-cli/src/mcp/tools.rs b/problemreductions-cli/src/mcp/tools.rs index 89d45627..420b9e78 100644 --- a/problemreductions-cli/src/mcp/tools.rs +++ b/problemreductions-cli/src/mcp/tools.rs @@ -3,9 +3,10 @@ use problemreductions::models::graph::{ MaxCut, MaximumClique, MaximumIndependentSet, MaximumMatching, MinimumDominatingSet, MinimumVertexCover, TravelingSalesman, }; -use problemreductions::models::optimization::{SpinGlass, QUBO}; -use problemreductions::models::satisfiability::{CNFClause, Satisfiability}; -use problemreductions::models::specialized::Factoring; +use problemreductions::models::algebraic::QUBO; +use problemreductions::models::formula::{CNFClause, Satisfiability}; +use problemreductions::models::graph::SpinGlass; +use problemreductions::models::misc::Factoring; use problemreductions::registry::collect_schemas; use problemreductions::rules::{ CustomCost, MinimizeSteps, ReductionGraph, ReductionPath, TraversalDirection, diff --git a/src/models/algebraic/bmf.rs b/src/models/algebraic/bmf.rs index fcccb5d3..552f82cc 100644 --- a/src/models/algebraic/bmf.rs +++ b/src/models/algebraic/bmf.rs @@ -34,7 +34,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::specialized::BMF; +/// use problemreductions::models::algebraic::BMF; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // 2x2 identity matrix diff --git a/src/models/algebraic/closest_vector_problem.rs b/src/models/algebraic/closest_vector_problem.rs index 94a0a30b..fe5d69c4 100644 --- a/src/models/algebraic/closest_vector_problem.rs +++ b/src/models/algebraic/closest_vector_problem.rs @@ -3,7 +3,7 @@ //! Given a lattice basis B and target vector t, find integer coefficients x //! minimizing ‖Bx - t‖₂. -use crate::models::optimization::VarBounds; +use crate::models::algebraic::VarBounds; use crate::registry::{FieldInfo, ProblemSchemaEntry}; use crate::traits::{OptimizationProblem, Problem}; use crate::types::{Direction, SolutionSize}; diff --git a/src/models/algebraic/ilp.rs b/src/models/algebraic/ilp.rs index 9d7624a5..fe2c31f6 100644 --- a/src/models/algebraic/ilp.rs +++ b/src/models/algebraic/ilp.rs @@ -195,7 +195,7 @@ pub enum ObjectiveSense { /// # Example /// /// ``` -/// use problemreductions::models::optimization::{ILP, VarBounds, Comparison, LinearConstraint, ObjectiveSense}; +/// use problemreductions::models::algebraic::{ILP, VarBounds, Comparison, LinearConstraint, ObjectiveSense}; /// use problemreductions::Problem; /// /// // Create a simple ILP: maximize x0 + 2*x1 diff --git a/src/models/algebraic/qubo.rs b/src/models/algebraic/qubo.rs index 9553888d..1e30f35b 100644 --- a/src/models/algebraic/qubo.rs +++ b/src/models/algebraic/qubo.rs @@ -33,7 +33,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::optimization::QUBO; +/// use problemreductions::models::algebraic::QUBO; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // Q matrix: minimize x0 - 2*x1 + x0*x1 diff --git a/src/models/formula/circuit.rs b/src/models/formula/circuit.rs index 55e9e803..383f5a6b 100644 --- a/src/models/formula/circuit.rs +++ b/src/models/formula/circuit.rs @@ -195,7 +195,7 @@ impl Circuit { /// # Example /// /// ``` -/// use problemreductions::models::specialized::{CircuitSAT, BooleanExpr, Assignment, Circuit}; +/// use problemreductions::models::formula::{CircuitSAT, BooleanExpr, Assignment, Circuit}; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // Create a simple circuit: c = x AND y diff --git a/src/models/formula/ksat.rs b/src/models/formula/ksat.rs index 67983ddc..4a542efb 100644 --- a/src/models/formula/ksat.rs +++ b/src/models/formula/ksat.rs @@ -37,7 +37,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::satisfiability::{KSatisfiability, CNFClause}; +/// use problemreductions::models::formula::{KSatisfiability, CNFClause}; /// use problemreductions::variant::K3; /// use problemreductions::{Problem, Solver, BruteForce}; /// diff --git a/src/models/formula/sat.rs b/src/models/formula/sat.rs index 080822b8..448f58fa 100644 --- a/src/models/formula/sat.rs +++ b/src/models/formula/sat.rs @@ -89,7 +89,7 @@ impl CNFClause { /// # Example /// /// ``` -/// use problemreductions::models::satisfiability::{Satisfiability, CNFClause}; +/// use problemreductions::models::formula::{Satisfiability, CNFClause}; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // Formula: (x1 OR x2) AND (NOT x1 OR x3) AND (NOT x2 OR NOT x3) diff --git a/src/models/graph/biclique_cover.rs b/src/models/graph/biclique_cover.rs index e29c6406..77bb9e5c 100644 --- a/src/models/graph/biclique_cover.rs +++ b/src/models/graph/biclique_cover.rs @@ -32,7 +32,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::specialized::BicliqueCover; +/// use problemreductions::models::graph::BicliqueCover; /// use problemreductions::topology::BipartiteGraph; /// use problemreductions::{Problem, Solver, BruteForce}; /// diff --git a/src/models/graph/spin_glass.rs b/src/models/graph/spin_glass.rs index 136fda44..30bf90ac 100644 --- a/src/models/graph/spin_glass.rs +++ b/src/models/graph/spin_glass.rs @@ -42,7 +42,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::optimization::SpinGlass; +/// use problemreductions::models::graph::SpinGlass; /// use problemreductions::topology::SimpleGraph; /// use problemreductions::{Problem, Solver, BruteForce}; /// diff --git a/src/models/misc/bin_packing.rs b/src/models/misc/bin_packing.rs index 45d5c1c5..cfa1647c 100644 --- a/src/models/misc/bin_packing.rs +++ b/src/models/misc/bin_packing.rs @@ -39,7 +39,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::optimization::BinPacking; +/// use problemreductions::models::misc::BinPacking; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // 4 items with sizes [3, 3, 2, 2], capacity 5 diff --git a/src/models/misc/factoring.rs b/src/models/misc/factoring.rs index 7d7524fd..f4408a72 100644 --- a/src/models/misc/factoring.rs +++ b/src/models/misc/factoring.rs @@ -29,7 +29,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::specialized::Factoring; +/// use problemreductions::models::misc::Factoring; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // Factor 6 with 2-bit factors (allowing factors 0-3) diff --git a/src/models/misc/paintshop.rs b/src/models/misc/paintshop.rs index b83ba407..1fe68272 100644 --- a/src/models/misc/paintshop.rs +++ b/src/models/misc/paintshop.rs @@ -33,7 +33,7 @@ inventory::submit! { /// # Example /// /// ``` -/// use problemreductions::models::specialized::PaintShop; +/// use problemreductions::models::misc::PaintShop; /// use problemreductions::{Problem, Solver, BruteForce}; /// /// // Sequence: a, b, a, c, c, b diff --git a/src/solvers/ilp/mod.rs b/src/solvers/ilp/mod.rs index d6169058..8244962c 100644 --- a/src/solvers/ilp/mod.rs +++ b/src/solvers/ilp/mod.rs @@ -6,7 +6,7 @@ //! # Example //! //! ```rust,ignore -//! use problemreductions::models::optimization::{ILP, VarBounds, LinearConstraint, ObjectiveSense}; +//! use problemreductions::models::algebraic::{ILP, VarBounds, LinearConstraint, ObjectiveSense}; //! use problemreductions::solvers::ILPSolver; //! //! // Create a simple ILP: maximize x0 + 2*x1 subject to x0 + x1 <= 1 diff --git a/src/solvers/ilp/solver.rs b/src/solvers/ilp/solver.rs index a6525bb9..23744dc5 100644 --- a/src/solvers/ilp/solver.rs +++ b/src/solvers/ilp/solver.rs @@ -1,6 +1,6 @@ //! ILP solver implementation using HiGHS. -use crate::models::optimization::{Comparison, ObjectiveSense, ILP}; +use crate::models::algebraic::{Comparison, ObjectiveSense, ILP}; use crate::rules::{ReduceTo, ReductionResult}; use good_lp::{default_solver, variable, ProblemVariables, Solution, SolverModel, Variable}; @@ -11,7 +11,7 @@ use good_lp::{default_solver, variable, ProblemVariables, Solution, SolverModel, /// # Example /// /// ```rust,ignore -/// use problemreductions::models::optimization::{ILP, VarBounds, LinearConstraint, ObjectiveSense}; +/// use problemreductions::models::algebraic::{ILP, VarBounds, LinearConstraint, ObjectiveSense}; /// use problemreductions::solvers::ILPSolver; /// /// // Create a simple ILP: maximize x0 + 2*x1 subject to x0 + x1 <= 1 diff --git a/src/unit_tests/jl_helpers.rs b/src/unit_tests/jl_helpers.rs index d45c68a8..cb51d27a 100644 --- a/src/unit_tests/jl_helpers.rs +++ b/src/unit_tests/jl_helpers.rs @@ -81,7 +81,7 @@ fn jl_parse_sets(val: &serde_json::Value) -> Vec> { #[allow(dead_code)] fn jl_parse_sat_clauses( instance: &serde_json::Value, -) -> (usize, Vec) { +) -> (usize, Vec) { let num_vars = instance["num_variables"] .as_u64() .expect("num_variables should be a u64") as usize; @@ -105,7 +105,7 @@ fn jl_parse_sat_clauses( if negated { -var } else { var } }) .collect(); - crate::models::satisfiability::CNFClause::new(literals) + crate::models::formula::CNFClause::new(literals) }) .collect(); (num_vars, clauses) diff --git a/src/unit_tests/problem_size.rs b/src/unit_tests/problem_size.rs index 7c7669b9..52116df9 100644 --- a/src/unit_tests/problem_size.rs +++ b/src/unit_tests/problem_size.rs @@ -1,10 +1,10 @@ //! Tests for problem_size() free function and Problem size implementations. +use crate::models::algebraic::*; +use crate::models::formula::*; use crate::models::graph::*; -use crate::models::optimization::*; -use crate::models::satisfiability::*; +use crate::models::misc::*; use crate::models::set::*; -use crate::models::specialized::*; use crate::topology::{BipartiteGraph, SimpleGraph}; use crate::traits::{problem_size, Problem}; @@ -94,7 +94,7 @@ fn test_problem_size_tsp() { #[test] fn test_problem_size_sat() { - use crate::models::satisfiability::CNFClause; + use crate::models::formula::CNFClause; let sat = Satisfiability::new( 3, vec![CNFClause::new(vec![1, -2]), CNFClause::new(vec![2, 3])], @@ -107,7 +107,7 @@ fn test_problem_size_sat() { #[test] fn test_problem_size_ksat() { - use crate::models::satisfiability::CNFClause; + use crate::models::formula::CNFClause; use crate::variant::K3; let ksat = KSatisfiability::::new( 3, @@ -143,7 +143,7 @@ fn test_problem_size_spinglass() { #[test] fn test_problem_size_ilp() { - use crate::models::optimization::{LinearConstraint, ObjectiveSense}; + use crate::models::algebraic::{LinearConstraint, ObjectiveSense}; let ilp = ILP::binary( 2, vec![LinearConstraint::le(vec![(0, 1.0), (1, 1.0)], 3.0)], @@ -165,7 +165,7 @@ fn test_problem_size_factoring() { #[test] fn test_problem_size_circuitsat() { - use crate::models::specialized::{Assignment, BooleanExpr, Circuit}; + use crate::models::formula::{Assignment, BooleanExpr, Circuit}; let circuit = Circuit::new(vec![Assignment::new( vec!["c".to_string()], BooleanExpr::and(vec![BooleanExpr::var("x"), BooleanExpr::var("y")]), diff --git a/src/unit_tests/reduction_graph.rs b/src/unit_tests/reduction_graph.rs index 6bb979ac..dd62524c 100644 --- a/src/unit_tests/reduction_graph.rs +++ b/src/unit_tests/reduction_graph.rs @@ -1,6 +1,6 @@ //! Tests for ReductionGraph: discovery, path finding, and typed API. -use crate::models::satisfiability::KSatisfiability; +use crate::models::formula::KSatisfiability; use crate::prelude::*; use crate::rules::{MinimizeSteps, ReductionGraph, TraversalDirection}; use crate::topology::{SimpleGraph, TriangularSubgraph}; @@ -74,7 +74,7 @@ fn test_multi_step_path() { let graph = ReductionGraph::new(); // Factoring -> CircuitSAT -> SpinGlass is a 2-step path - let src = ReductionGraph::variant_to_map(&crate::models::specialized::Factoring::variant()); + let src = ReductionGraph::variant_to_map(&crate::models::misc::Factoring::variant()); let dst = ReductionGraph::variant_to_map(&SpinGlass::::variant()); let path = graph.find_cheapest_path( "Factoring", @@ -279,7 +279,7 @@ fn test_reduction_path_display() { #[test] fn test_3sat_to_mis_triangular_overhead() { - use crate::models::satisfiability::CNFClause; + use crate::models::formula::CNFClause; let graph = ReductionGraph::new(); diff --git a/src/unit_tests/rules/circuit_ilp.rs b/src/unit_tests/rules/circuit_ilp.rs index 3b2b54a3..3e7bf257 100644 --- a/src/unit_tests/rules/circuit_ilp.rs +++ b/src/unit_tests/rules/circuit_ilp.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::specialized::{Assignment, BooleanExpr, Circuit, CircuitSAT}; +use crate::models::formula::{Assignment, BooleanExpr, Circuit, CircuitSAT}; use crate::solvers::BruteForce; use std::collections::HashSet; diff --git a/src/unit_tests/rules/circuit_spinglass.rs b/src/unit_tests/rules/circuit_spinglass.rs index 6342a128..e0331e02 100644 --- a/src/unit_tests/rules/circuit_spinglass.rs +++ b/src/unit_tests/rules/circuit_spinglass.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::specialized::Circuit; +use crate::models::formula::Circuit; use crate::solvers::BruteForce; use crate::types::{NumericSize, WeightElement}; use num_traits::Num; @@ -276,7 +276,7 @@ fn test_solution_extraction() { #[test] fn test_jl_parity_circuitsat_to_spinglass() { - use crate::models::specialized::{Assignment, BooleanExpr, Circuit}; + use crate::models::formula::{Assignment, BooleanExpr, Circuit}; let a = BooleanExpr::var("a"); let b = BooleanExpr::var("b"); let c = BooleanExpr::var("c"); diff --git a/src/unit_tests/rules/graph.rs b/src/unit_tests/rules/graph.rs index 357d64f6..eed173e3 100644 --- a/src/unit_tests/rules/graph.rs +++ b/src/unit_tests/rules/graph.rs @@ -1,6 +1,6 @@ use super::*; use crate::models::graph::{MaximumIndependentSet, MinimumVertexCover}; -use crate::models::optimization::QUBO; +use crate::models::algebraic::QUBO; use crate::models::set::MaximumSetPacking; use crate::rules::cost::MinimizeSteps; use crate::rules::graph::{classify_problem_category, ReductionStep}; @@ -82,7 +82,7 @@ fn test_variant_level_paths() { let src = ReductionGraph::variant_to_map( &crate::models::graph::MaxCut::::variant(), ); - let dst = ReductionGraph::variant_to_map(&crate::models::optimization::SpinGlass::< + let dst = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< SimpleGraph, i32, >::variant()); @@ -94,7 +94,7 @@ fn test_variant_level_paths() { let src_f64 = ReductionGraph::variant_to_map( &crate::models::graph::MaxCut::::variant(), ); - let dst_f64 = ReductionGraph::variant_to_map(&crate::models::optimization::SpinGlass::< + let dst_f64 = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< SimpleGraph, f64, >::variant()); @@ -110,7 +110,7 @@ fn test_find_shortest_path_variants() { let src = ReductionGraph::variant_to_map( &crate::models::graph::MaxCut::::variant(), ); - let dst = ReductionGraph::variant_to_map(&crate::models::optimization::SpinGlass::< + let dst = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< SimpleGraph, i32, >::variant()); @@ -125,8 +125,8 @@ fn test_find_shortest_path_variants() { assert!(shortest.is_some()); assert_eq!(shortest.unwrap().len(), 1); // Direct path - let src = ReductionGraph::variant_to_map(&crate::models::specialized::Factoring::variant()); - let dst = ReductionGraph::variant_to_map(&crate::models::optimization::SpinGlass::< + let src = ReductionGraph::variant_to_map(&crate::models::misc::Factoring::variant()); + let dst = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< SimpleGraph, i32, >::variant()); @@ -216,7 +216,7 @@ fn test_to_json() { assert!(json.nodes.len() >= 10); assert!(json.nodes.iter().any(|n| n.name == "MaximumIndependentSet")); assert!(json.nodes.iter().any(|n| n.category == "graph")); - assert!(json.nodes.iter().any(|n| n.category == "optimization")); + assert!(json.nodes.iter().any(|n| n.category == "algebraic")); // Check edges assert!(json.edges.len() >= 10); @@ -268,18 +268,18 @@ fn test_category_from_module_path() { "set" ); assert_eq!( - ReductionGraph::category_from_module_path("problemreductions::models::optimization::qubo"), - "optimization" + ReductionGraph::category_from_module_path("problemreductions::models::algebraic::qubo"), + "algebraic" ); assert_eq!( - ReductionGraph::category_from_module_path("problemreductions::models::satisfiability::sat"), - "satisfiability" + ReductionGraph::category_from_module_path("problemreductions::models::formula::sat"), + "formula" ); assert_eq!( ReductionGraph::category_from_module_path( - "problemreductions::models::specialized::factoring" + "problemreductions::models::misc::factoring" ), - "specialized" + "misc" ); // Fallback for unexpected format assert_eq!( @@ -299,10 +299,10 @@ fn test_doc_path_from_module_path() { ); assert_eq!( ReductionGraph::doc_path_from_module_path( - "problemreductions::models::optimization::qubo", + "problemreductions::models::algebraic::qubo", "QUBO" ), - "models/optimization/struct.QUBO.html" + "models/algebraic/struct.QUBO.html" ); } @@ -310,7 +310,7 @@ fn test_doc_path_from_module_path() { fn test_sat_based_reductions() { use crate::models::graph::KColoring; use crate::models::graph::MinimumDominatingSet; - use crate::models::satisfiability::Satisfiability; + use crate::models::formula::Satisfiability; use crate::variant::K3; let graph = ReductionGraph::new(); @@ -327,8 +327,9 @@ fn test_sat_based_reductions() { #[test] fn test_circuit_reductions() { - use crate::models::optimization::SpinGlass; - use crate::models::specialized::{CircuitSAT, Factoring}; + use crate::models::formula::CircuitSAT; + use crate::models::graph::SpinGlass; + use crate::models::misc::Factoring; let graph = ReductionGraph::new(); @@ -359,7 +360,8 @@ fn test_circuit_reductions() { #[test] fn test_optimization_reductions() { use crate::models::graph::MaxCut; - use crate::models::optimization::{SpinGlass, QUBO}; + use crate::models::algebraic::QUBO; + use crate::models::graph::SpinGlass; let graph = ReductionGraph::new(); @@ -374,7 +376,7 @@ fn test_optimization_reductions() { #[test] fn test_ksat_reductions() { - use crate::models::satisfiability::{KSatisfiability, Satisfiability}; + use crate::models::formula::{KSatisfiability, Satisfiability}; use crate::variant::K3; let graph = ReductionGraph::new(); @@ -394,9 +396,9 @@ fn test_all_categories_present() { assert!(categories.contains("graph")); assert!(categories.contains("set")); - assert!(categories.contains("optimization")); - assert!(categories.contains("satisfiability")); - assert!(categories.contains("specialized")); + assert!(categories.contains("algebraic")); + assert!(categories.contains("formula")); + assert!(categories.contains("misc")); } #[test] @@ -499,7 +501,7 @@ fn test_category_derived_from_schema() { let graph = ReductionGraph::new(); let json = graph.to_json(); let circuit = json.nodes.iter().find(|n| n.name == "CircuitSAT").unwrap(); - assert_eq!(circuit.category, "specialized"); + assert_eq!(circuit.category, "formula"); } #[test] @@ -779,16 +781,16 @@ fn test_classify_problem_category() { "graph" ); assert_eq!( - classify_problem_category("problemreductions::models::satisfiability::satisfiability"), - "satisfiability" + classify_problem_category("problemreductions::models::formula::satisfiability"), + "formula" ); assert_eq!( classify_problem_category("problemreductions::models::set::maximum_set_packing"), "set" ); assert_eq!( - classify_problem_category("problemreductions::models::optimization::qubo"), - "optimization" + classify_problem_category("problemreductions::models::algebraic::qubo"), + "algebraic" ); assert_eq!(classify_problem_category("unknown::path"), "other"); } @@ -889,7 +891,7 @@ fn test_reduction_chain_multi_step() { #[test] fn test_reduction_chain_with_variant_casts() { - use crate::models::satisfiability::{CNFClause, KSatisfiability}; + use crate::models::formula::{CNFClause, KSatisfiability}; use crate::rules::MinimizeSteps; use crate::solvers::{BruteForce, Solver}; use crate::topology::UnitDiskGraph; diff --git a/src/unit_tests/rules/ilp_qubo.rs b/src/unit_tests/rules/ilp_qubo.rs index c3568f01..df21dc98 100644 --- a/src/unit_tests/rules/ilp_qubo.rs +++ b/src/unit_tests/rules/ilp_qubo.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::optimization::{LinearConstraint, ObjectiveSense}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense}; use crate::solvers::BruteForce; use crate::traits::Problem; diff --git a/src/unit_tests/rules/ksatisfiability_qubo.rs b/src/unit_tests/rules/ksatisfiability_qubo.rs index a3ec43e6..ac7fe8d6 100644 --- a/src/unit_tests/rules/ksatisfiability_qubo.rs +++ b/src/unit_tests/rules/ksatisfiability_qubo.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::satisfiability::CNFClause; +use crate::models::formula::CNFClause; use crate::solvers::BruteForce; use crate::traits::Problem; use crate::variant::{K2, K3}; diff --git a/src/unit_tests/rules/reduction_path_parity.rs b/src/unit_tests/rules/reduction_path_parity.rs index a655b418..f84244a1 100644 --- a/src/unit_tests/rules/reduction_path_parity.rs +++ b/src/unit_tests/rules/reduction_path_parity.rs @@ -2,9 +2,9 @@ //! Verifies that chained reductions via `find_cheapest_path` + `reduce_along_path` //! produce correct solutions matching direct source solves. -use crate::models::graph::MaxCut; -use crate::models::optimization::{SpinGlass, QUBO}; -use crate::models::specialized::Factoring; +use crate::models::algebraic::QUBO; +use crate::models::graph::{MaxCut, SpinGlass}; +use crate::models::misc::Factoring; use crate::rules::{MinimizeSteps, ReductionGraph}; use crate::solvers::{BruteForce, Solver}; use crate::topology::SimpleGraph; diff --git a/src/unit_tests/rules/registry.rs b/src/unit_tests/rules/registry.rs index 4fc5f5cc..fb9c3b09 100644 --- a/src/unit_tests/rules/registry.rs +++ b/src/unit_tests/rules/registry.rs @@ -231,7 +231,7 @@ fn test_overhead_eval_fn_cross_check_mis_to_mvc() { #[test] fn test_overhead_eval_fn_cross_check_factoring_to_ilp() { - use crate::models::specialized::Factoring; + use crate::models::misc::Factoring; let problem = Factoring::new(3, 4, 42); @@ -273,7 +273,7 @@ fn test_complexity_eval_fn_cross_check_mis() { #[test] fn test_complexity_eval_fn_cross_check_factoring() { - use crate::models::specialized::Factoring; + use crate::models::misc::Factoring; use crate::registry::VariantEntry; let problem = Factoring::new(8, 8, 100); diff --git a/src/unit_tests/rules/sat_circuitsat.rs b/src/unit_tests/rules/sat_circuitsat.rs index 019c6e81..dd028a7c 100644 --- a/src/unit_tests/rules/sat_circuitsat.rs +++ b/src/unit_tests/rules/sat_circuitsat.rs @@ -1,6 +1,5 @@ use super::*; -use crate::models::satisfiability::{CNFClause, Satisfiability}; -use crate::models::specialized::CircuitSAT; +use crate::models::formula::{CNFClause, CircuitSAT, Satisfiability}; use crate::rules::ReduceTo; use crate::solvers::BruteForce; use crate::traits::Problem; diff --git a/src/unit_tests/rules/sat_coloring.rs b/src/unit_tests/rules/sat_coloring.rs index 456b3c8f..7d7847b9 100644 --- a/src/unit_tests/rules/sat_coloring.rs +++ b/src/unit_tests/rules/sat_coloring.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::satisfiability::CNFClause; +use crate::models::formula::CNFClause; use crate::solvers::BruteForce; use crate::topology::Graph; use crate::variant::K3; diff --git a/src/unit_tests/rules/sat_maximumindependentset.rs b/src/unit_tests/rules/sat_maximumindependentset.rs index b60f40a5..ce85a7eb 100644 --- a/src/unit_tests/rules/sat_maximumindependentset.rs +++ b/src/unit_tests/rules/sat_maximumindependentset.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::satisfiability::CNFClause; +use crate::models::formula::CNFClause; use crate::solvers::BruteForce; use crate::topology::Graph; use crate::traits::Problem; diff --git a/src/unit_tests/rules/sat_minimumdominatingset.rs b/src/unit_tests/rules/sat_minimumdominatingset.rs index e6ae2405..8627613b 100644 --- a/src/unit_tests/rules/sat_minimumdominatingset.rs +++ b/src/unit_tests/rules/sat_minimumdominatingset.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::satisfiability::CNFClause; +use crate::models::formula::CNFClause; use crate::solvers::BruteForce; use crate::topology::Graph; use crate::traits::Problem; diff --git a/src/unit_tests/solvers/brute_force.rs b/src/unit_tests/solvers/brute_force.rs index 19561c01..2e80628e 100644 --- a/src/unit_tests/solvers/brute_force.rs +++ b/src/unit_tests/solvers/brute_force.rs @@ -262,7 +262,7 @@ fn test_solver_with_real_mis() { #[test] fn test_solver_with_real_sat() { - use crate::models::satisfiability::{CNFClause, Satisfiability}; + use crate::models::formula::{CNFClause, Satisfiability}; use crate::traits::Problem; // (x1 OR x2) AND (NOT x1 OR NOT x2) diff --git a/src/unit_tests/solvers/ilp/solver.rs b/src/unit_tests/solvers/ilp/solver.rs index abf5f831..20ff5ec2 100644 --- a/src/unit_tests/solvers/ilp/solver.rs +++ b/src/unit_tests/solvers/ilp/solver.rs @@ -1,5 +1,5 @@ use super::*; -use crate::models::optimization::{LinearConstraint, VarBounds}; +use crate::models::algebraic::{LinearConstraint, VarBounds}; use crate::solvers::BruteForce; use crate::traits::Problem; diff --git a/src/unit_tests/trait_consistency.rs b/src/unit_tests/trait_consistency.rs index 7c3fa2e2..7eef0660 100644 --- a/src/unit_tests/trait_consistency.rs +++ b/src/unit_tests/trait_consistency.rs @@ -1,8 +1,8 @@ +use crate::models::algebraic::*; +use crate::models::formula::*; use crate::models::graph::*; -use crate::models::optimization::*; -use crate::models::satisfiability::*; +use crate::models::misc::*; use crate::models::set::*; -use crate::models::specialized::*; use crate::topology::{BipartiteGraph, SimpleGraph}; use crate::traits::Problem; use crate::variant::K3; diff --git a/src/unit_tests/unitdiskmapping_algorithms/common.rs b/src/unit_tests/unitdiskmapping_algorithms/common.rs index 03d12de4..53e99169 100644 --- a/src/unit_tests/unitdiskmapping_algorithms/common.rs +++ b/src/unit_tests/unitdiskmapping_algorithms/common.rs @@ -1,6 +1,6 @@ //! Common test utilities for mapping tests. -use crate::models::optimization::{LinearConstraint, ObjectiveSense, ILP}; +use crate::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}; use crate::models::MaximumIndependentSet; use crate::rules::unitdiskmapping::MappingResult; use crate::rules::{ReduceTo, ReductionResult}; diff --git a/src/unit_tests/unitdiskmapping_algorithms/weighted.rs b/src/unit_tests/unitdiskmapping_algorithms/weighted.rs index 17189cc6..917a7977 100644 --- a/src/unit_tests/unitdiskmapping_algorithms/weighted.rs +++ b/src/unit_tests/unitdiskmapping_algorithms/weighted.rs @@ -657,7 +657,7 @@ fn test_square_danglinleg_weights() { #[test] fn test_weighted_map_config_back_standard_graphs() { use super::common::{is_independent_set, solve_mis}; - use crate::models::optimization::{LinearConstraint, ObjectiveSense, ILP}; + use crate::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}; use crate::solvers::ILPSolver; use crate::topology::smallgraph; diff --git a/src/unit_tests/variant.rs b/src/unit_tests/variant.rs index 90b582e2..91f04aab 100644 --- a/src/unit_tests/variant.rs +++ b/src/unit_tests/variant.rs @@ -83,10 +83,11 @@ fn test_variant_for_problems() { KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, MinimumDominatingSet, MinimumVertexCover, }; - use crate::models::optimization::{SpinGlass, QUBO}; - use crate::models::satisfiability::{KSatisfiability, Satisfiability}; + use crate::models::algebraic::{BMF, QUBO}; + use crate::models::formula::{CircuitSAT, KSatisfiability, Satisfiability}; + use crate::models::graph::{BicliqueCover, SpinGlass}; + use crate::models::misc::{Factoring, PaintShop}; use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; - use crate::models::specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; use crate::topology::SimpleGraph; use crate::traits::Problem; diff --git a/tests/suites/integration.rs b/tests/suites/integration.rs index 94ebd5be..49e43f6f 100644 --- a/tests/suites/integration.rs +++ b/tests/suites/integration.rs @@ -3,11 +3,11 @@ //! These tests verify that all problem types work correctly with the //! BruteForce solver and that related problems have consistent solutions. +use problemreductions::models::algebraic::*; +use problemreductions::models::formula::*; use problemreductions::models::graph::*; -use problemreductions::models::optimization::*; -use problemreductions::models::satisfiability::*; +use problemreductions::models::misc::*; use problemreductions::models::set::*; -use problemreductions::models::specialized::*; use problemreductions::prelude::*; use problemreductions::topology::{BipartiteGraph, SimpleGraph}; use problemreductions::variant::K3; diff --git a/tests/suites/reductions.rs b/tests/suites/reductions.rs index d757f2a1..daad3adc 100644 --- a/tests/suites/reductions.rs +++ b/tests/suites/reductions.rs @@ -3,7 +3,7 @@ //! These tests verify that reduction chains work correctly and //! solutions can be properly extracted through the reduction pipeline. -use problemreductions::models::optimization::{LinearConstraint, ObjectiveSense, ILP}; +use problemreductions::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}; use problemreductions::prelude::*; use problemreductions::topology::{Graph, SimpleGraph}; use problemreductions::variant::{K2, K3}; From d58d61502e203e2d05157e79f69308eb9d09ec0a Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:48:28 +0800 Subject: [PATCH 12/15] docs: update import paths in getting-started guide Co-Authored-By: Claude Opus 4.6 --- docs/src/getting-started.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/src/getting-started.md b/docs/src/getting-started.md index 49e502b5..9ba6ef3a 100644 --- a/docs/src/getting-started.md +++ b/docs/src/getting-started.md @@ -39,7 +39,7 @@ A path graph `0–1–2–3` has 4 vertices and 3 edges. ```rust,ignore use problemreductions::prelude::*; -use problemreductions::models::optimization::ILP; +use problemreductions::models::algebraic::ILP; use problemreductions::solvers::ILPSolver; use problemreductions::topology::SimpleGraph; From 979564c721d19499a51dd5e7497f4de79dc52f04 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:48:58 +0800 Subject: [PATCH 13/15] docs: update reduction graph colors for new categories Co-Authored-By: Claude Opus 4.6 --- docs/src/static/reduction-graph.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/docs/src/static/reduction-graph.js b/docs/src/static/reduction-graph.js index 76c15a17..c497f681 100644 --- a/docs/src/static/reduction-graph.js +++ b/docs/src/static/reduction-graph.js @@ -14,12 +14,12 @@ document.addEventListener('DOMContentLoaded', function() { } var categoryColors = { - graph: '#c8f0c8', set: '#f0c8c8', optimization: '#f0f0a0', - satisfiability: '#c8c8f0', specialized: '#f0c8e0' + graph: '#c8f0c8', set: '#f0c8c8', algebraic: '#f0f0a0', + formula: '#c8c8f0', misc: '#f0c8e0' }; var categoryBorders = { - graph: '#4a8c4a', set: '#8c4a4a', optimization: '#8c8c4a', - satisfiability: '#4a4a8c', specialized: '#8c4a6a' + graph: '#4a8c4a', set: '#8c4a4a', algebraic: '#8c8c4a', + formula: '#4a4a8c', misc: '#8c4a6a' }; function variantId(name, variant) { From 9940a5d91a47e986f6d6aa8e8c7b4887182b8a93 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 13:52:49 +0800 Subject: [PATCH 14/15] chore: format code and regenerate reduction graph artifacts Co-Authored-By: Claude Opus 4.6 --- docs/src/reductions/reduction_graph.json | 68 ++++++++++++------------ problemreductions-cli/src/mcp/tools.rs | 7 ++- src/lib.rs | 6 +-- src/models/formula/mod.rs | 2 +- src/models/mod.rs | 2 +- src/rules/circuit_spinglass.rs | 2 +- src/rules/coloring_ilp.rs | 2 +- src/rules/coloring_qubo.rs | 2 +- src/rules/maximumclique_ilp.rs | 2 +- src/rules/maximumindependentset_ilp.rs | 2 +- src/rules/maximumindependentset_qubo.rs | 2 +- src/rules/maximummatching_ilp.rs | 2 +- src/rules/minimumdominatingset_ilp.rs | 2 +- src/rules/minimumvertexcover_ilp.rs | 2 +- src/rules/minimumvertexcover_qubo.rs | 2 +- src/rules/sat_coloring.rs | 2 +- src/rules/sat_maximumindependentset.rs | 2 +- src/rules/sat_minimumdominatingset.rs | 2 +- src/rules/travelingsalesman_ilp.rs | 2 +- src/unit_tests/rules/graph.rs | 31 +++++------ src/unit_tests/variant.rs | 6 +-- 21 files changed, 72 insertions(+), 78 deletions(-) diff --git a/docs/src/reductions/reduction_graph.json b/docs/src/reductions/reduction_graph.json index 9cf34c21..0b0c6850 100644 --- a/docs/src/reductions/reduction_graph.json +++ b/docs/src/reductions/reduction_graph.json @@ -3,15 +3,15 @@ { "name": "BMF", "variant": {}, - "category": "specialized", - "doc_path": "models/specialized/struct.BMF.html", + "category": "algebraic", + "doc_path": "models/algebraic/struct.BMF.html", "complexity": "2^(rows * rank + rank * cols)" }, { "name": "BicliqueCover", "variant": {}, - "category": "specialized", - "doc_path": "models/specialized/struct.BicliqueCover.html", + "category": "graph", + "doc_path": "models/graph/struct.BicliqueCover.html", "complexity": "2^num_vertices" }, { @@ -19,8 +19,8 @@ "variant": { "weight": "f64" }, - "category": "optimization", - "doc_path": "models/optimization/struct.BinPacking.html", + "category": "misc", + "doc_path": "models/misc/struct.BinPacking.html", "complexity": "2^num_items" }, { @@ -28,15 +28,15 @@ "variant": { "weight": "i32" }, - "category": "optimization", - "doc_path": "models/optimization/struct.BinPacking.html", + "category": "misc", + "doc_path": "models/misc/struct.BinPacking.html", "complexity": "2^num_items" }, { "name": "CircuitSAT", "variant": {}, - "category": "specialized", - "doc_path": "models/specialized/struct.CircuitSAT.html", + "category": "formula", + "doc_path": "models/formula/struct.CircuitSAT.html", "complexity": "2^num_variables" }, { @@ -44,8 +44,8 @@ "variant": { "weight": "f64" }, - "category": "optimization", - "doc_path": "models/optimization/struct.ClosestVectorProblem.html", + "category": "algebraic", + "doc_path": "models/algebraic/struct.ClosestVectorProblem.html", "complexity": "2^num_basis_vectors" }, { @@ -53,22 +53,22 @@ "variant": { "weight": "i32" }, - "category": "optimization", - "doc_path": "models/optimization/struct.ClosestVectorProblem.html", + "category": "algebraic", + "doc_path": "models/algebraic/struct.ClosestVectorProblem.html", "complexity": "2^num_basis_vectors" }, { "name": "Factoring", "variant": {}, - "category": "specialized", - "doc_path": "models/specialized/struct.Factoring.html", + "category": "misc", + "doc_path": "models/misc/struct.Factoring.html", "complexity": "exp((m + n)^(1/3) * log(m + n)^(2/3))" }, { "name": "ILP", "variant": {}, - "category": "optimization", - "doc_path": "models/optimization/struct.ILP.html", + "category": "algebraic", + "doc_path": "models/algebraic/struct.ILP.html", "complexity": "num_variables^num_variables" }, { @@ -126,8 +126,8 @@ "variant": { "k": "K2" }, - "category": "satisfiability", - "doc_path": "models/satisfiability/struct.KSatisfiability.html", + "category": "formula", + "doc_path": "models/formula/struct.KSatisfiability.html", "complexity": "num_variables + num_clauses" }, { @@ -135,8 +135,8 @@ "variant": { "k": "K3" }, - "category": "satisfiability", - "doc_path": "models/satisfiability/struct.KSatisfiability.html", + "category": "formula", + "doc_path": "models/formula/struct.KSatisfiability.html", "complexity": "1.307^num_variables" }, { @@ -144,8 +144,8 @@ "variant": { "k": "KN" }, - "category": "satisfiability", - "doc_path": "models/satisfiability/struct.KSatisfiability.html", + "category": "formula", + "doc_path": "models/formula/struct.KSatisfiability.html", "complexity": "2^num_variables" }, { @@ -317,8 +317,8 @@ { "name": "PaintShop", "variant": {}, - "category": "specialized", - "doc_path": "models/specialized/struct.PaintShop.html", + "category": "misc", + "doc_path": "models/misc/struct.PaintShop.html", "complexity": "2^num_cars" }, { @@ -326,15 +326,15 @@ "variant": { "weight": "f64" }, - "category": "optimization", - "doc_path": "models/optimization/struct.QUBO.html", + "category": "algebraic", + "doc_path": "models/algebraic/struct.QUBO.html", "complexity": "2^num_vars" }, { "name": "Satisfiability", "variant": {}, - "category": "satisfiability", - "doc_path": "models/satisfiability/struct.Satisfiability.html", + "category": "formula", + "doc_path": "models/formula/struct.Satisfiability.html", "complexity": "2^num_variables" }, { @@ -343,8 +343,8 @@ "graph": "SimpleGraph", "weight": "f64" }, - "category": "optimization", - "doc_path": "models/optimization/struct.SpinGlass.html", + "category": "graph", + "doc_path": "models/graph/struct.SpinGlass.html", "complexity": "2^num_spins" }, { @@ -353,8 +353,8 @@ "graph": "SimpleGraph", "weight": "i32" }, - "category": "optimization", - "doc_path": "models/optimization/struct.SpinGlass.html", + "category": "graph", + "doc_path": "models/graph/struct.SpinGlass.html", "complexity": "2^num_spins" }, { diff --git a/problemreductions-cli/src/mcp/tools.rs b/problemreductions-cli/src/mcp/tools.rs index 420b9e78..f7a94026 100644 --- a/problemreductions-cli/src/mcp/tools.rs +++ b/problemreductions-cli/src/mcp/tools.rs @@ -1,11 +1,10 @@ use crate::util; +use problemreductions::models::algebraic::QUBO; +use problemreductions::models::formula::{CNFClause, Satisfiability}; use problemreductions::models::graph::{ MaxCut, MaximumClique, MaximumIndependentSet, MaximumMatching, MinimumDominatingSet, - MinimumVertexCover, TravelingSalesman, + MinimumVertexCover, SpinGlass, TravelingSalesman, }; -use problemreductions::models::algebraic::QUBO; -use problemreductions::models::formula::{CNFClause, Satisfiability}; -use problemreductions::models::graph::SpinGlass; use problemreductions::models::misc::Factoring; use problemreductions::registry::collect_schemas; use problemreductions::rules::{ diff --git a/src/lib.rs b/src/lib.rs index 15e10d49..ef67ab53 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -36,13 +36,13 @@ pub mod variant; /// Prelude module for convenient imports. pub mod prelude { // Problem types + pub use crate::models::algebraic::{BMF, QUBO}; + pub use crate::models::formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; + pub use crate::models::graph::{BicliqueCover, SpinGlass}; pub use crate::models::graph::{ KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, MinimumDominatingSet, MinimumVertexCover, TravelingSalesman, }; - pub use crate::models::algebraic::{QUBO, BMF}; - pub use crate::models::formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; - pub use crate::models::graph::{BicliqueCover, SpinGlass}; pub use crate::models::misc::{BinPacking, Factoring, PaintShop}; pub use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; diff --git a/src/models/formula/mod.rs b/src/models/formula/mod.rs index b5a14ed2..f2a33cce 100644 --- a/src/models/formula/mod.rs +++ b/src/models/formula/mod.rs @@ -5,9 +5,9 @@ //! - [`KSatisfiability`]: K-SAT where each clause has exactly K literals //! - [`CircuitSAT`]: Boolean circuit satisfiability +pub(crate) mod circuit; mod ksat; mod sat; -pub(crate) mod circuit; pub use circuit::{Assignment, BooleanExpr, BooleanOp, Circuit, CircuitSAT}; pub use ksat::KSatisfiability; diff --git a/src/models/mod.rs b/src/models/mod.rs index fbf18ed9..15df5cfa 100644 --- a/src/models/mod.rs +++ b/src/models/mod.rs @@ -9,7 +9,7 @@ pub mod misc; pub mod set; // Re-export commonly used types -pub use algebraic::{ClosestVectorProblem, ILP, QUBO, BMF}; +pub use algebraic::{ClosestVectorProblem, BMF, ILP, QUBO}; pub use formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; pub use graph::{ BicliqueCover, KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, diff --git a/src/rules/circuit_spinglass.rs b/src/rules/circuit_spinglass.rs index 8c392aeb..86473227 100644 --- a/src/rules/circuit_spinglass.rs +++ b/src/rules/circuit_spinglass.rs @@ -6,8 +6,8 @@ //! Each logic gate is encoded as a SpinGlass Hamiltonian where the ground //! states correspond to valid input/output combinations. -use crate::models::graph::SpinGlass; use crate::models::formula::{Assignment, BooleanExpr, BooleanOp, CircuitSAT}; +use crate::models::graph::SpinGlass; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::SimpleGraph; diff --git a/src/rules/coloring_ilp.rs b/src/rules/coloring_ilp.rs index eb93af77..5bd45c26 100644 --- a/src/rules/coloring_ilp.rs +++ b/src/rules/coloring_ilp.rs @@ -7,8 +7,8 @@ //! 2. Adjacent vertices have different colors: x_{u,c} + x_{v,c} <= 1 for each edge (u,v) and color c //! - Objective: None (feasibility problem, minimize 0) -use crate::models::graph::KColoring; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::KColoring; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/coloring_qubo.rs b/src/rules/coloring_qubo.rs index c5062baf..e94975f0 100644 --- a/src/rules/coloring_qubo.rs +++ b/src/rules/coloring_qubo.rs @@ -8,8 +8,8 @@ //! //! QUBO has n*K variables. -use crate::models::graph::KColoring; use crate::models::algebraic::QUBO; +use crate::models::graph::KColoring; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximumclique_ilp.rs b/src/rules/maximumclique_ilp.rs index 4d968009..0b36bba2 100644 --- a/src/rules/maximumclique_ilp.rs +++ b/src/rules/maximumclique_ilp.rs @@ -6,8 +6,8 @@ //! at most one can be in the clique //! - Objective: Maximize the sum of weights of selected vertices -use crate::models::graph::MaximumClique; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::MaximumClique; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximumindependentset_ilp.rs b/src/rules/maximumindependentset_ilp.rs index 7313afea..10a02f2c 100644 --- a/src/rules/maximumindependentset_ilp.rs +++ b/src/rules/maximumindependentset_ilp.rs @@ -5,8 +5,8 @@ //! - Constraints: x_u + x_v <= 1 for each edge (u, v) - at most one endpoint can be selected //! - Objective: Maximize the sum of weights of selected vertices -use crate::models::graph::MaximumIndependentSet; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::MaximumIndependentSet; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximumindependentset_qubo.rs b/src/rules/maximumindependentset_qubo.rs index fe3a4592..2d0b4dae 100644 --- a/src/rules/maximumindependentset_qubo.rs +++ b/src/rules/maximumindependentset_qubo.rs @@ -5,8 +5,8 @@ //! //! Q[i][i] = -w_i, Q[i][j] = P for edges. P = 1 + Σ w_i. -use crate::models::graph::MaximumIndependentSet; use crate::models::algebraic::QUBO; +use crate::models::graph::MaximumIndependentSet; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/maximummatching_ilp.rs b/src/rules/maximummatching_ilp.rs index aa19cda5..04c86793 100644 --- a/src/rules/maximummatching_ilp.rs +++ b/src/rules/maximummatching_ilp.rs @@ -6,8 +6,8 @@ //! (at most one incident edge can be selected) //! - Objective: Maximize the sum of weights of selected edges -use crate::models::graph::MaximumMatching; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::MaximumMatching; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/minimumdominatingset_ilp.rs b/src/rules/minimumdominatingset_ilp.rs index ce246e92..e2981a81 100644 --- a/src/rules/minimumdominatingset_ilp.rs +++ b/src/rules/minimumdominatingset_ilp.rs @@ -6,8 +6,8 @@ //! (v or at least one of its neighbors must be selected) //! - Objective: Minimize the sum of weights of selected vertices -use crate::models::graph::MinimumDominatingSet; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::MinimumDominatingSet; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/minimumvertexcover_ilp.rs b/src/rules/minimumvertexcover_ilp.rs index dea767a3..d69c0232 100644 --- a/src/rules/minimumvertexcover_ilp.rs +++ b/src/rules/minimumvertexcover_ilp.rs @@ -5,8 +5,8 @@ //! - Constraints: x_u + x_v >= 1 for each edge (u, v) - at least one endpoint must be selected //! - Objective: Minimize the sum of weights of selected vertices -use crate::models::graph::MinimumVertexCover; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::MinimumVertexCover; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/minimumvertexcover_qubo.rs b/src/rules/minimumvertexcover_qubo.rs index 99c38d0b..a47e0cd5 100644 --- a/src/rules/minimumvertexcover_qubo.rs +++ b/src/rules/minimumvertexcover_qubo.rs @@ -6,8 +6,8 @@ //! Expanding: Q[i][i] = w_i - P·deg(i), Q[i][j] = P for edges. //! P = 1 + Σ w_i. -use crate::models::graph::MinimumVertexCover; use crate::models::algebraic::QUBO; +use crate::models::graph::MinimumVertexCover; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/rules/sat_coloring.rs b/src/rules/sat_coloring.rs index 05c61ffc..0c6bb4bc 100644 --- a/src/rules/sat_coloring.rs +++ b/src/rules/sat_coloring.rs @@ -8,8 +8,8 @@ //! 3. For each clause, build an OR-gadget that forces output to be TRUE color //! - The OR-gadget is built recursively for multi-literal clauses -use crate::models::graph::KColoring; use crate::models::formula::Satisfiability; +use crate::models::graph::KColoring; use crate::reduction; use crate::rules::sat_maximumindependentset::BoolVar; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/sat_maximumindependentset.rs b/src/rules/sat_maximumindependentset.rs index b601b792..de28824e 100644 --- a/src/rules/sat_maximumindependentset.rs +++ b/src/rules/sat_maximumindependentset.rs @@ -8,8 +8,8 @@ //! A satisfying assignment corresponds to an independent set of size = num_clauses, //! where we pick exactly one literal from each clause. -use crate::models::graph::MaximumIndependentSet; use crate::models::formula::Satisfiability; +use crate::models::graph::MaximumIndependentSet; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::SimpleGraph; diff --git a/src/rules/sat_minimumdominatingset.rs b/src/rules/sat_minimumdominatingset.rs index a4cb80a6..ac0cf052 100644 --- a/src/rules/sat_minimumdominatingset.rs +++ b/src/rules/sat_minimumdominatingset.rs @@ -14,8 +14,8 @@ //! - Selecting the negative literal vertex means the variable is false //! - Selecting the dummy vertex means the variable can be either (unused in any clause) -use crate::models::graph::MinimumDominatingSet; use crate::models::formula::Satisfiability; +use crate::models::graph::MinimumDominatingSet; use crate::reduction; use crate::rules::sat_maximumindependentset::BoolVar; use crate::rules::traits::{ReduceTo, ReductionResult}; diff --git a/src/rules/travelingsalesman_ilp.rs b/src/rules/travelingsalesman_ilp.rs index d00e48c5..5b5cc796 100644 --- a/src/rules/travelingsalesman_ilp.rs +++ b/src/rules/travelingsalesman_ilp.rs @@ -5,8 +5,8 @@ //! - Constraints: assignment, non-edge consecutive, McCormick //! - Objective: minimize total edge weight of the tour -use crate::models::graph::TravelingSalesman; use crate::models::algebraic::{LinearConstraint, ObjectiveSense, VarBounds, ILP}; +use crate::models::graph::TravelingSalesman; use crate::reduction; use crate::rules::traits::{ReduceTo, ReductionResult}; use crate::topology::{Graph, SimpleGraph}; diff --git a/src/unit_tests/rules/graph.rs b/src/unit_tests/rules/graph.rs index eed173e3..b9d54db6 100644 --- a/src/unit_tests/rules/graph.rs +++ b/src/unit_tests/rules/graph.rs @@ -1,6 +1,6 @@ use super::*; -use crate::models::graph::{MaximumIndependentSet, MinimumVertexCover}; use crate::models::algebraic::QUBO; +use crate::models::graph::{MaximumIndependentSet, MinimumVertexCover}; use crate::models::set::MaximumSetPacking; use crate::rules::cost::MinimizeSteps; use crate::rules::graph::{classify_problem_category, ReductionStep}; @@ -82,10 +82,9 @@ fn test_variant_level_paths() { let src = ReductionGraph::variant_to_map( &crate::models::graph::MaxCut::::variant(), ); - let dst = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< - SimpleGraph, - i32, - >::variant()); + let dst = ReductionGraph::variant_to_map( + &crate::models::graph::SpinGlass::::variant(), + ); let paths = graph.find_all_paths("MaxCut", &src, "SpinGlass", &dst); assert!(!paths.is_empty()); assert_eq!(paths[0].type_names(), vec!["MaxCut", "SpinGlass"]); @@ -110,10 +109,9 @@ fn test_find_shortest_path_variants() { let src = ReductionGraph::variant_to_map( &crate::models::graph::MaxCut::::variant(), ); - let dst = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< - SimpleGraph, - i32, - >::variant()); + let dst = ReductionGraph::variant_to_map( + &crate::models::graph::SpinGlass::::variant(), + ); let shortest = graph.find_cheapest_path( "MaxCut", &src, @@ -126,10 +124,9 @@ fn test_find_shortest_path_variants() { assert_eq!(shortest.unwrap().len(), 1); // Direct path let src = ReductionGraph::variant_to_map(&crate::models::misc::Factoring::variant()); - let dst = ReductionGraph::variant_to_map(&crate::models::graph::SpinGlass::< - SimpleGraph, - i32, - >::variant()); + let dst = ReductionGraph::variant_to_map( + &crate::models::graph::SpinGlass::::variant(), + ); let shortest = graph.find_cheapest_path( "Factoring", &src, @@ -276,9 +273,7 @@ fn test_category_from_module_path() { "formula" ); assert_eq!( - ReductionGraph::category_from_module_path( - "problemreductions::models::misc::factoring" - ), + ReductionGraph::category_from_module_path("problemreductions::models::misc::factoring"), "misc" ); // Fallback for unexpected format @@ -308,9 +303,9 @@ fn test_doc_path_from_module_path() { #[test] fn test_sat_based_reductions() { + use crate::models::formula::Satisfiability; use crate::models::graph::KColoring; use crate::models::graph::MinimumDominatingSet; - use crate::models::formula::Satisfiability; use crate::variant::K3; let graph = ReductionGraph::new(); @@ -359,8 +354,8 @@ fn test_circuit_reductions() { #[test] fn test_optimization_reductions() { - use crate::models::graph::MaxCut; use crate::models::algebraic::QUBO; + use crate::models::graph::MaxCut; use crate::models::graph::SpinGlass; let graph = ReductionGraph::new(); diff --git a/src/unit_tests/variant.rs b/src/unit_tests/variant.rs index 91f04aab..13753324 100644 --- a/src/unit_tests/variant.rs +++ b/src/unit_tests/variant.rs @@ -79,13 +79,13 @@ fn test_variant_params_macro_multiple() { #[test] fn test_variant_for_problems() { + use crate::models::algebraic::{BMF, QUBO}; + use crate::models::formula::{CircuitSAT, KSatisfiability, Satisfiability}; + use crate::models::graph::{BicliqueCover, SpinGlass}; use crate::models::graph::{ KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, MinimumDominatingSet, MinimumVertexCover, }; - use crate::models::algebraic::{BMF, QUBO}; - use crate::models::formula::{CircuitSAT, KSatisfiability, Satisfiability}; - use crate::models::graph::{BicliqueCover, SpinGlass}; use crate::models::misc::{Factoring, PaintShop}; use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; use crate::topology::SimpleGraph; From 5e951d0ce3ca334d389bf1752dc10b5f0049e679 Mon Sep 17 00:00:00 2001 From: GiggleLiu Date: Sun, 1 Mar 2026 14:07:02 +0800 Subject: [PATCH 15/15] chore: remove completed implementation plan The step-by-step implementation plan has been fully executed. The design doc (2026-03-01-problem-categorization-design.md) remains as it documents the reasoning behind the change. Co-Authored-By: Claude Opus 4.6 --- .../2026-03-01-problem-categorization-impl.md | 618 ------------------ 1 file changed, 618 deletions(-) delete mode 100644 docs/plans/2026-03-01-problem-categorization-impl.md diff --git a/docs/plans/2026-03-01-problem-categorization-impl.md b/docs/plans/2026-03-01-problem-categorization-impl.md deleted file mode 100644 index 7654661a..00000000 --- a/docs/plans/2026-03-01-problem-categorization-impl.md +++ /dev/null @@ -1,618 +0,0 @@ -# Problem Categorization Refactoring Implementation Plan - -> **For Claude:** REQUIRED SUB-SKILL: Use superpowers:executing-plans to implement this plan task-by-task. - -**Goal:** Move problem model files from the old mixed-axis categories (`optimization/`, `satisfiability/`, `specialized/`) to new input-structure-based categories (`formula/`, `algebraic/`, `misc/`), keeping `graph/` and `set/` unchanged. - -**Architecture:** Pure file-move refactoring. The `classify_problem_category()` function in `src/rules/graph.rs` automatically derives categories from `module_path!()`, so moving files is sufficient — no classification logic changes. The `graph/` and `set/` modules are untouched. The `satisfiability/` module is renamed to `formula/` (with CircuitSAT added). The `optimization/` and `specialized/` modules are eliminated. - -**Tech Stack:** Rust, `git mv`, `make check` - -**Key reference:** Design doc at `docs/plans/2026-03-01-problem-categorization-design.md` - ---- - -### Task 1: Create new module directories and move source files - -**Files:** -- Create: `src/models/formula/mod.rs`, `src/models/algebraic/mod.rs`, `src/models/misc/mod.rs` -- Move (git mv): 13 source files between directories -- Delete: `src/models/optimization/`, `src/models/satisfiability/`, `src/models/specialized/` (after moves) - -**Step 1: Move satisfiability/ → formula/ (rename + add CircuitSAT)** - -```bash -# Rename the directory -git mv src/models/satisfiability src/models/formula - -# Move CircuitSAT from specialized/ to formula/ -git mv src/models/specialized/circuit.rs src/models/formula/circuit.rs -``` - -**Step 2: Create algebraic/ and move files into it** - -```bash -mkdir -p src/models/algebraic - -git mv src/models/optimization/qubo.rs src/models/algebraic/qubo.rs -git mv src/models/optimization/ilp.rs src/models/algebraic/ilp.rs -git mv src/models/optimization/closest_vector_problem.rs src/models/algebraic/closest_vector_problem.rs -git mv src/models/specialized/bmf.rs src/models/algebraic/bmf.rs -``` - -**Step 3: Create misc/ and move files into it** - -```bash -mkdir -p src/models/misc - -git mv src/models/optimization/bin_packing.rs src/models/misc/bin_packing.rs -git mv src/models/specialized/factoring.rs src/models/misc/factoring.rs -git mv src/models/specialized/paintshop.rs src/models/misc/paintshop.rs -``` - -**Step 4: Move SpinGlass and BicliqueCover into graph/** - -```bash -git mv src/models/optimization/spin_glass.rs src/models/graph/spin_glass.rs -git mv src/models/specialized/biclique_cover.rs src/models/graph/biclique_cover.rs -``` - -**Step 5: Remove now-empty old directories** - -```bash -# optimization/ and specialized/ should be empty except for mod.rs -rm src/models/optimization/mod.rs -rmdir src/models/optimization -rm src/models/specialized/mod.rs -rmdir src/models/specialized -``` - -**Step 6: Commit** - -```bash -git add -A src/models/ -git commit -m "refactor: move model files to input-structure-based categories" -``` - ---- - -### Task 2: Update mod.rs files for new module structure - -**Files:** -- Modify: `src/models/mod.rs` -- Modify: `src/models/formula/mod.rs` (was satisfiability/mod.rs) -- Create: `src/models/algebraic/mod.rs` -- Create: `src/models/misc/mod.rs` -- Modify: `src/models/graph/mod.rs` - -**Step 1: Update `src/models/mod.rs`** - -Replace entire contents with: - -```rust -//! Problem model implementations. -//! -//! Each sub-module groups related problem types by input structure. - -pub mod algebraic; -pub mod formula; -pub mod graph; -pub mod misc; -pub mod set; - -// Re-export commonly used types -pub use algebraic::{BinPacking, ClosestVectorProblem, SpinGlass, ILP, QUBO}; -pub use formula::{CNFClause, KSatisfiability, Satisfiability}; -pub use graph::{ - KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, MaximumMatching, - MinimumDominatingSet, MinimumVertexCover, TravelingSalesman, -}; -pub use set::{MaximumSetPacking, MinimumSetCovering}; -pub use specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; -``` - -Wait — re-exports need to come from the *new* modules. Correct version: - -```rust -//! Problem model implementations. -//! -//! Each sub-module groups related problem types by input structure. - -pub mod algebraic; -pub mod formula; -pub mod graph; -pub mod misc; -pub mod set; - -// Re-export commonly used types -pub use algebraic::{ClosestVectorProblem, ILP, QUBO, BMF}; -pub use formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; -pub use graph::{ - BicliqueCover, KColoring, MaxCut, MaximalIS, MaximumClique, MaximumIndependentSet, - MaximumMatching, MinimumDominatingSet, MinimumVertexCover, SpinGlass, TravelingSalesman, -}; -pub use misc::{BinPacking, Factoring, PaintShop}; -pub use set::{MaximumSetPacking, MinimumSetCovering}; -``` - -**Step 2: Update `src/models/formula/mod.rs` (was satisfiability/mod.rs)** - -Replace entire contents with: - -```rust -//! Logic and formula problems. -//! -//! Problems whose input is a boolean formula or circuit: -//! - [`Satisfiability`]: Boolean satisfiability (SAT) with CNF clauses -//! - [`KSatisfiability`]: K-SAT where each clause has exactly K literals -//! - [`CircuitSAT`]: Boolean circuit satisfiability - -mod ksat; -mod sat; -pub(crate) mod circuit; - -pub use circuit::{Assignment, BooleanExpr, BooleanOp, Circuit, CircuitSAT}; -pub use ksat::KSatisfiability; -pub use sat::{CNFClause, Satisfiability}; -``` - -**Step 3: Write `src/models/algebraic/mod.rs`** - -```rust -//! Algebraic problems. -//! -//! Problems whose input is a matrix, linear system, or lattice: -//! - [`QUBO`]: Quadratic Unconstrained Binary Optimization -//! - [`ILP`]: Integer Linear Programming -//! - [`ClosestVectorProblem`]: Closest Vector Problem (minimize lattice distance) -//! - [`BMF`]: Boolean Matrix Factorization - -pub(crate) mod bmf; -mod closest_vector_problem; -mod ilp; -mod qubo; - -pub use bmf::BMF; -pub use closest_vector_problem::ClosestVectorProblem; -pub use ilp::{Comparison, LinearConstraint, ObjectiveSense, VarBounds, ILP}; -pub use qubo::QUBO; -``` - -**Step 4: Write `src/models/misc/mod.rs`** - -```rust -//! Miscellaneous problems. -//! -//! Problems with unique input structures that don't fit other categories: -//! - [`BinPacking`]: Bin Packing (minimize bins) -//! - [`Factoring`]: Integer factorization -//! - [`PaintShop`]: Minimize color switches in paint shop scheduling - -mod bin_packing; -pub(crate) mod factoring; -pub(crate) mod paintshop; - -pub use bin_packing::BinPacking; -pub use factoring::Factoring; -pub use paintshop::PaintShop; -``` - -**Step 5: Update `src/models/graph/mod.rs`** — add SpinGlass and BicliqueCover - -Add to the module declarations (maintaining alphabetical order and `pub(crate)` visibility where the old modules used it): - -```rust -//! Graph problems. -//! -//! Problems whose input is a graph (optionally weighted): -//! - [`MaximumIndependentSet`]: Maximum weight independent set -//! - [`MaximalIS`]: Maximal independent set -//! - [`MinimumVertexCover`]: Minimum weight vertex cover -//! - [`MinimumDominatingSet`]: Minimum dominating set -//! - [`MaximumClique`]: Maximum weight clique -//! - [`MaxCut`]: Maximum cut on weighted graphs -//! - [`KColoring`]: K-vertex coloring -//! - [`MaximumMatching`]: Maximum weight matching -//! - [`TravelingSalesman`]: Traveling Salesman (minimum weight Hamiltonian cycle) -//! - [`SpinGlass`]: Ising model Hamiltonian -//! - [`BicliqueCover`]: Biclique cover on bipartite graphs - -pub(crate) mod biclique_cover; -pub(crate) mod kcoloring; -pub(crate) mod max_cut; -pub(crate) mod maximal_is; -pub(crate) mod maximum_clique; -pub(crate) mod maximum_independent_set; -pub(crate) mod maximum_matching; -pub(crate) mod minimum_dominating_set; -pub(crate) mod minimum_vertex_cover; -pub(crate) mod spin_glass; -pub(crate) mod traveling_salesman; - -pub use biclique_cover::BicliqueCover; -pub use kcoloring::KColoring; -pub use max_cut::MaxCut; -pub use maximal_is::MaximalIS; -pub use maximum_clique::MaximumClique; -pub use maximum_independent_set::MaximumIndependentSet; -pub use maximum_matching::MaximumMatching; -pub use minimum_dominating_set::MinimumDominatingSet; -pub use minimum_vertex_cover::MinimumVertexCover; -pub use spin_glass::SpinGlass; -pub use traveling_salesman::TravelingSalesman; -``` - -**Step 6: Commit** - -```bash -git add src/models/ -git commit -m "refactor: update mod.rs files for new category structure" -``` - ---- - -### Task 3: Move unit test files to match new source structure - -The unit tests mirror the source directory layout under `src/unit_tests/models/`. - -**Files:** -- Move: 12 unit test files to new directories -- Create: `src/unit_tests/models/formula/`, `src/unit_tests/models/algebraic/`, `src/unit_tests/models/misc/` - -**Step 1: Move test files** - -```bash -# formula/ (rename satisfiability/ + add circuit) -git mv src/unit_tests/models/satisfiability src/unit_tests/models/formula -git mv src/unit_tests/models/specialized/circuit.rs src/unit_tests/models/formula/circuit.rs - -# algebraic/ -mkdir -p src/unit_tests/models/algebraic -git mv src/unit_tests/models/optimization/qubo.rs src/unit_tests/models/algebraic/qubo.rs -git mv src/unit_tests/models/optimization/ilp.rs src/unit_tests/models/algebraic/ilp.rs -git mv src/unit_tests/models/optimization/closest_vector_problem.rs src/unit_tests/models/algebraic/closest_vector_problem.rs -git mv src/unit_tests/models/specialized/bmf.rs src/unit_tests/models/algebraic/bmf.rs - -# misc/ -mkdir -p src/unit_tests/models/misc -git mv src/unit_tests/models/optimization/bin_packing.rs src/unit_tests/models/misc/bin_packing.rs -git mv src/unit_tests/models/specialized/factoring.rs src/unit_tests/models/misc/factoring.rs -git mv src/unit_tests/models/specialized/paintshop.rs src/unit_tests/models/misc/paintshop.rs - -# graph/ (add spin_glass and biclique_cover) -git mv src/unit_tests/models/optimization/spin_glass.rs src/unit_tests/models/graph/spin_glass.rs -git mv src/unit_tests/models/specialized/biclique_cover.rs src/unit_tests/models/graph/biclique_cover.rs - -# Remove empty old directories -rmdir src/unit_tests/models/optimization -rmdir src/unit_tests/models/specialized -``` - -**Step 2: Update `#[path]` attributes in moved source files** - -Each model source file has a `#[cfg(test)] #[path = "..."]` attribute pointing to its test file. After the moves, these relative paths are still correct because both source and test moved by the same amount — **except** for files that changed category (e.g., spin_glass moved from `optimization/` to `graph/`). - -Update these `#[path]` attributes in the **source** files: - -| Source file (new location) | Old `#[path]` | New `#[path]` | -|---|---|---| -| `src/models/formula/sat.rs` | `../../unit_tests/models/satisfiability/sat.rs` | `../../unit_tests/models/formula/sat.rs` | -| `src/models/formula/ksat.rs` | `../../unit_tests/models/satisfiability/ksat.rs` | `../../unit_tests/models/formula/ksat.rs` | -| `src/models/formula/circuit.rs` | `../../unit_tests/models/specialized/circuit.rs` | `../../unit_tests/models/formula/circuit.rs` | -| `src/models/algebraic/qubo.rs` | `../../unit_tests/models/optimization/qubo.rs` | `../../unit_tests/models/algebraic/qubo.rs` | -| `src/models/algebraic/ilp.rs` | `../../unit_tests/models/optimization/ilp.rs` | `../../unit_tests/models/algebraic/ilp.rs` | -| `src/models/algebraic/closest_vector_problem.rs` | `../../unit_tests/models/optimization/closest_vector_problem.rs` | `../../unit_tests/models/algebraic/closest_vector_problem.rs` | -| `src/models/algebraic/bmf.rs` | `../../unit_tests/models/specialized/bmf.rs` | `../../unit_tests/models/algebraic/bmf.rs` | -| `src/models/misc/bin_packing.rs` | `../../unit_tests/models/optimization/bin_packing.rs` | `../../unit_tests/models/misc/bin_packing.rs` | -| `src/models/misc/factoring.rs` | `../../unit_tests/models/specialized/factoring.rs` | `../../unit_tests/models/misc/factoring.rs` | -| `src/models/misc/paintshop.rs` | `../../unit_tests/models/specialized/paintshop.rs` | `../../unit_tests/models/misc/paintshop.rs` | -| `src/models/graph/spin_glass.rs` | `../../unit_tests/models/optimization/spin_glass.rs` | `../../unit_tests/models/graph/spin_glass.rs` | -| `src/models/graph/biclique_cover.rs` | `../../unit_tests/models/specialized/biclique_cover.rs` | `../../unit_tests/models/graph/biclique_cover.rs` | - -Use grep to find the exact `#[path` line in each file and update it. - -**Step 3: Commit** - -```bash -git add -A src/unit_tests/models/ src/models/ -git commit -m "refactor: move unit tests to match new category structure" -``` - ---- - -### Task 4: Update all `use` imports in `src/rules/` - -Every reduction rule file imports problem types via `crate::models::::...`. These must be updated to the new category paths. - -**Files:** ~27 files in `src/rules/` - -**Replacements (find and replace across all files in `src/rules/`):** - -| Old import path | New import path | -|---|---| -| `crate::models::optimization::SpinGlass` | `crate::models::graph::SpinGlass` | -| `crate::models::optimization::QUBO` | `crate::models::algebraic::QUBO` | -| `crate::models::optimization::{...ILP...}` | `crate::models::algebraic::{...ILP...}` | -| `crate::models::optimization::BinPacking` | `crate::models::misc::BinPacking` | -| `crate::models::optimization::ClosestVectorProblem` | `crate::models::algebraic::ClosestVectorProblem` | -| `crate::models::satisfiability::Satisfiability` | `crate::models::formula::Satisfiability` | -| `crate::models::satisfiability::KSatisfiability` | `crate::models::formula::KSatisfiability` | -| `crate::models::satisfiability::{CNFClause, ...}` | `crate::models::formula::{CNFClause, ...}` | -| `crate::models::specialized::CircuitSAT` | `crate::models::formula::CircuitSAT` | -| `crate::models::specialized::{Assignment, BooleanExpr, ...Circuit...}` | `crate::models::formula::{Assignment, BooleanExpr, ...Circuit...}` | -| `crate::models::specialized::Factoring` | `crate::models::misc::Factoring` | -| `crate::models::specialized::PaintShop` | `crate::models::misc::PaintShop` | -| `crate::models::specialized::BicliqueCover` | `crate::models::graph::BicliqueCover` | -| `crate::models::specialized::BMF` | `crate::models::algebraic::BMF` | - -**Approach:** For each file in `src/rules/`, read it, identify any `use crate::models::{optimization,satisfiability,specialized}` lines, and update them. Many files import from multiple old categories, so some may need imports split into multiple `use` statements. - -Specific files to update (grouped by what they import): - -**ILP imports (optimization → algebraic):** `ilp_qubo.rs`, `qubo_ilp.rs`, `minimumsetcovering_ilp.rs`, `minimumvertexcover_ilp.rs`, `maximummatching_ilp.rs`, `circuit_ilp.rs`, `coloring_ilp.rs`, `maximumclique_ilp.rs`, `maximumindependentset_ilp.rs`, `maximumsetpacking_ilp.rs`, `travelingsalesman_ilp.rs`, `minimumdominatingset_ilp.rs`, `factoring_ilp.rs` - -**QUBO imports (optimization → algebraic):** `spinglass_qubo.rs`, `maximumsetpacking_qubo.rs`, `ksatisfiability_qubo.rs`, `minimumvertexcover_qubo.rs`, `maximumindependentset_qubo.rs`, `coloring_qubo.rs`, `ilp_qubo.rs` - -**SpinGlass imports (optimization → graph):** `spinglass_qubo.rs`, `spinglass_maxcut.rs`, `spinglass_casts.rs`, `circuit_spinglass.rs` - -**Satisfiability imports (satisfiability → formula):** `sat_coloring.rs`, `sat_ksat.rs`, `sat_maximumindependentset.rs`, `sat_minimumdominatingset.rs`, `sat_circuitsat.rs`, `ksatisfiability_qubo.rs`, `ksatisfiability_casts.rs` - -**CircuitSAT/Circuit imports (specialized → formula):** `circuit_spinglass.rs`, `circuit_ilp.rs`, `factoring_circuit.rs`, `sat_circuitsat.rs` - -**Factoring imports (specialized → misc):** `factoring_circuit.rs`, `factoring_ilp.rs` - -**Step: Commit** - -```bash -git add src/rules/ -git commit -m "refactor: update rule imports for new model categories" -``` - ---- - -### Task 5: Update `src/lib.rs` prelude and doc comments - -**Files:** -- Modify: `src/lib.rs` - -**Step 1: Update the API overview doc comment (line 10)** - -Change: -```rust -//! | [`models`] | Problem types — [`graph`](models::graph), [`satisfiability`](models::satisfiability), [`set`](models::set), [`optimization`](models::optimization), [`specialized`](models::specialized) | -``` -To: -```rust -//! | [`models`] | Problem types — [`graph`](models::graph), [`formula`](models::formula), [`set`](models::set), [`algebraic`](models::algebraic), [`misc`](models::misc) | -``` - -**Step 2: Update the prelude module (lines 43-46)** - -Change: -```rust - pub use crate::models::optimization::{SpinGlass, QUBO}; - pub use crate::models::satisfiability::{CNFClause, KSatisfiability, Satisfiability}; - pub use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; - pub use crate::models::specialized::{BicliqueCover, CircuitSAT, Factoring, PaintShop, BMF}; -``` -To: -```rust - pub use crate::models::algebraic::{QUBO, BMF}; - pub use crate::models::formula::{CNFClause, CircuitSAT, KSatisfiability, Satisfiability}; - pub use crate::models::graph::{BicliqueCover, SpinGlass}; - pub use crate::models::misc::{BinPacking, Factoring, PaintShop}; - pub use crate::models::set::{MaximumSetPacking, MinimumSetCovering}; -``` - -**Step 3: Commit** - -```bash -git add src/lib.rs -git commit -m "refactor: update lib.rs prelude and docs for new categories" -``` - ---- - -### Task 6: Update test imports and category assertions - -**Files:** -- Modify: `tests/suites/integration.rs` -- Modify: `tests/suites/reductions.rs` -- Modify: `src/unit_tests/rules/graph.rs` - -**Step 1: Update `tests/suites/integration.rs` (lines 7-10)** - -Change: -```rust -use problemreductions::models::optimization::*; -use problemreductions::models::satisfiability::*; -use problemreductions::models::set::*; -use problemreductions::models::specialized::*; -``` -To: -```rust -use problemreductions::models::algebraic::*; -use problemreductions::models::formula::*; -use problemreductions::models::misc::*; -use problemreductions::models::set::*; -``` - -**Step 2: Update `tests/suites/reductions.rs` (line 6)** - -Change: -```rust -use problemreductions::models::optimization::{LinearConstraint, ObjectiveSense, ILP}; -``` -To: -```rust -use problemreductions::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}; -``` - -**Step 3: Update category assertions in `src/unit_tests/rules/graph.rs`** - -| Line | Old assertion | New assertion | -|------|---|---| -| 219 | `n.category == "optimization"` | `n.category == "algebraic"` | -| 271-272 | `"optimization"` | `"algebraic"` | -| 275-276 | `"satisfiability"` | `"formula"` | -| 281-282 | `"specialized"` | `"misc"` | -| 397 | `categories.contains("optimization")` | `categories.contains("algebraic")` | -| 398 | `categories.contains("satisfiability")` | `categories.contains("formula")` | -| 399 | `categories.contains("specialized")` | `categories.contains("misc")` | -| 502 | `circuit.category, "specialized"` | `circuit.category, "formula"` | -| 782-783 | `"satisfiability"` | `"formula"` | -| 790-791 | `"optimization"` | `"algebraic"` | - -Also update the module path strings in the test assertions (lines 270-282): -- `"problemreductions::models::optimization::qubo"` → `"problemreductions::models::algebraic::qubo"` -- `"problemreductions::models::satisfiability::sat"` → `"problemreductions::models::formula::sat"` -- `"problemreductions::models::specialized::factoring"` → `"problemreductions::models::misc::factoring"` - -And in `test_classify_problem_category` (lines 781-791): -- `"problemreductions::models::satisfiability::satisfiability"` → `"problemreductions::models::formula::satisfiability"` -- `"problemreductions::models::optimization::qubo"` → `"problemreductions::models::algebraic::qubo"` - -**Step 4: Commit** - -```bash -git add tests/ src/unit_tests/ -git commit -m "refactor: update test imports and category assertions" -``` - ---- - -### Task 7: Update example imports - -**Files:** ~15 files in `examples/` - -**Replacements:** - -| Old import | New import | -|---|---| -| `problemreductions::models::optimization::ILP` | `problemreductions::models::algebraic::ILP` | -| `problemreductions::models::optimization::{LinearConstraint, ObjectiveSense, ILP}` | `problemreductions::models::algebraic::{LinearConstraint, ObjectiveSense, ILP}` | -| `problemreductions::models::specialized::{Assignment, BooleanExpr, Circuit}` | `problemreductions::models::formula::{Assignment, BooleanExpr, Circuit}` | -| `problemreductions::models::specialized::{Assignment, BooleanExpr, Circuit, CircuitSAT}` | `problemreductions::models::formula::{Assignment, BooleanExpr, Circuit, CircuitSAT}` | - -Affected example files: -- All `reduction_*_to_ilp.rs` files (ILP import) -- `reduction_ilp_to_qubo.rs` (ILP import) -- `reduction_circuitsat_to_ilp.rs` (ILP + Circuit imports) -- `reduction_factoring_to_circuitsat.rs` (Circuit import) -- `reduction_circuitsat_to_spinglass.rs` (Circuit import) - -**Step: Commit** - -```bash -git add examples/ -git commit -m "refactor: update example imports for new categories" -``` - ---- - -### Task 8: Update documentation references - -**Files:** -- Modify: `docs/src/getting-started.md` (line 42) -- Modify: `docs/src/design.md` (module overview table) - -**Step 1: Update `docs/src/getting-started.md`** - -Change: -```rust -use problemreductions::models::optimization::ILP; -``` -To: -```rust -use problemreductions::models::algebraic::ILP; -``` - -**Step 2: Update `docs/src/design.md` module table** (already done partially in earlier commit — verify the line is correct) - -**Step 3: Commit** - -```bash -git add docs/ -git commit -m "docs: update import paths in getting-started guide" -``` - ---- - -### Task 9: Update reduction graph visualization colors - -**Files:** -- Modify: `docs/src/static/reduction-graph.js` (lines 16-23) - -**Step 1: Update `categoryColors` and `categoryBorders`** - -Change: -```javascript -var categoryColors = { - graph: '#c8f0c8', set: '#f0c8c8', optimization: '#f0f0a0', - satisfiability: '#c8c8f0', specialized: '#f0c8e0' -}; -var categoryBorders = { - graph: '#4a8c4a', set: '#8c4a4a', optimization: '#8c8c4a', - satisfiability: '#4a4a8c', specialized: '#8c4a6a' -}; -``` -To: -```javascript -var categoryColors = { - graph: '#c8f0c8', set: '#f0c8c8', algebraic: '#f0f0a0', - formula: '#c8c8f0', misc: '#f0c8e0' -}; -var categoryBorders = { - graph: '#4a8c4a', set: '#8c4a4a', algebraic: '#8c8c4a', - formula: '#4a4a8c', misc: '#8c4a6a' -}; -``` - -**Step 2: Commit** - -```bash -git add docs/src/static/reduction-graph.js -git commit -m "docs: update reduction graph colors for new categories" -``` - ---- - -### Task 10: Build, test, and regenerate artifacts - -**Step 1: Run `make check` to verify everything compiles and passes** - -```bash -make check -``` - -Expected: All fmt, clippy, and test checks pass. If there are compilation errors, they will point to remaining old import paths that were missed — fix them. - -**Step 2: Regenerate the reduction graph JSON (categories are derived from module paths)** - -```bash -cargo run --example export_graph -cargo run --example export_schemas -``` - -This regenerates `docs/src/reductions/reduction_graph.json` and `docs/src/reductions/problem_schemas.json` with the new category values. - -**Step 3: Build mdbook to verify visualization** - -```bash -make doc -``` - -**Step 4: Commit regenerated artifacts** - -```bash -git add docs/src/reductions/ docs/book/ -git commit -m "chore: regenerate reduction graph with new categories" -``` - -**Step 5: Run full test suite one final time** - -```bash -make check -``` - -Expected: All green.