Skip to content

merge: expose fast-merge config levers + TPS warp + optimal-site seeding (backward-compatible)#227

Merged
mat10d merged 6 commits into
mainfrom
merge-fast-path-levers
Jul 10, 2026
Merged

merge: expose fast-merge config levers + TPS warp + optimal-site seeding (backward-compatible)#227
mat10d merged 6 commits into
mainfrom
merge-fast-path-levers

Conversation

@mat10d

@mat10d mat10d commented Jul 10, 2026

Copy link
Copy Markdown
Collaborator

What

Lands the fast-merge improvements onto main as 3 focused, backward-compatible commits, cherry-picked from merge-rotation-fix (which is stacked on the zarr3 line — this PR deliberately excludes all zarr3 changes):

  1. feat(merge): expose hardcoded fast-merge levers as backward-compatible config params — parameterizes the formerly-hardcoded knobs (threshold_triangle/point/region, ransac_kwargs, evaluate_kwargs+batch_size, warp degree/iterations/min_correspondences). All config.get(...) default None → lib literal. Defaults unchanged ⇒ existing screens byte-identical.
  2. feat(merge): thin-plate-spline warp + find-optimal-site seeding (gated) — adds two gated levers: local_refinement="thin_plate_spline" (with warp_smoothing/warp_max_correspondences) and find-optimal-site seeding (seed_optimize/seed_topk). Both default off ⇒ byte-identical to the affine/nearest-tile path.
  3. style(merge): single-line comments, lib high->low order, ruff format — house-style cleanup of the merge fast-path (no behavioral change).

Scope

Only 6 files, all in the merge path:
workflow/lib/merge/{fast_merge,hash}.py, workflow/scripts/merge/{fast_alignment,fast_merge}.py, workflow/rules/merge.smk, tests/test_merge_levers.py. No zarr3 / OME-Zarr / HCS files.

Testing

  • tests/test_merge_levers.py (shipped with commit 1) — 3/3 pass: verifies new kwargs at old literals == no kwargs (byte-identical defaults).
  • ruff format + check clean; all changed files compile.
  • Full small_test_analysis pipeline gate: running on Slurm; result to follow before merge.

Notes

Conflict resolution vs main: kept main's required-param semantics (det_range/score/threshold stay bracket-access) and main's config["merge"].get(...) style; added the new optional levers in that same style.

🤖 Generated with Claude Code

mat10d and others added 3 commits July 10, 2026 09:21
…e config params

Parameterize the formerly-hardcoded fast-merge knobs so they can be tuned per screen:
- evaluate_match: threshold_triangle, threshold_point, threshold_region, ransac_kwargs
- initial_alignment / multistep_alignment: evaluate_kwargs (+ batch_size)
- refine_local_warp: degree, iterations, min_correspondences via warp_kwargs,
  threaded through merge_triangle_hash / merge_sbs_phenotype
Wired through scripts/merge/{fast_alignment,fast_merge}.py and rules/merge.smk
(all config.get default None -> lib literal). Defaults unchanged => existing
screens byte-identical.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SAWdQnZAy3WU6bdxy41EgP
Adds two validated two-scope merge levers, both backward-compatible (defaults
off -> byte-identical to the affine path already on this branch):

- TPS warp: `local_refinement` now doubles as the warp-model selector
  ("polynomial" | "thin_plate_spline"); wire `warp_smoothing` /
  `warp_max_correspondences` through scripts/merge/fast_merge.py + merge.smk.
  On two-scope OPS merges TPS roughly halves the median residual vs polynomial
  while staying stable. String selector is byte-identical to an explicit
  warp_kwargs["model"]; a bare truthy keeps the polynomial default.

- find-optimal-site (`seed_optimize`, `seed_topk`): the stage-nearest phenotype
  tile is not always the best real overlap when the two scopes have a
  metadata-alignment residual. When on, evaluate the top-K nearest tiles per SBS
  seed and keep the highest-scoring one per site. Default off = nearest-tile,
  unchanged.

Verified: default (local_refinement=None, seed_optimize=False) path untouched;
polynomial selector == explicit model kwarg; TPS routes end-to-end and both
warps recover matches an affine drops on distorted data.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SAWdQnZAy3WU6bdxy41EgP
Cleanup of the merge fast-path (no behavioral change; smoke test identical):
- Collapse multiline block comments to single lines across fast_merge.py and
  fast_alignment.py.
- Reorder lib/merge/fast_merge.py high-level -> low-level: merge_triangle_hash,
  merge_sbs_phenotype, then helpers build_linear_model, refine_local_warp.
- Trim refine_local_warp docstring to the file's density; ruff format + check clean.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SAWdQnZAy3WU6bdxy41EgP
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@mat10d

mat10d commented Jul 10, 2026

Copy link
Copy Markdown
Collaborator Author

Full small_test_analysis gate passed on the branch — 2173/2173 steps (100%), snakemake exit 0, zero rule errors. All merge rules (fast_alignment, fast_merge, format_merge, deduplicate_merge, final_merge, eval_merge) ran and downstream aggregate/cluster consumed their outputs cleanly. Ran in the brieflow_test env on a compute node (default all-levers-unset path = byte-identical fallback).

mat10d and others added 2 commits July 10, 2026 10:42
…nobs

Per review of the merge autoresearch results, keep as config-exposed only the
levers with measured impact (threshold_triangle, ransac_random_state,
local_refinement, warp_degree/iterations/smoothing, seed_optimize/seed_topk).
Revert the inert knobs to hardcoded literals in the lib (threshold_point=2,
threshold_region=50, batch_size=180, warp min/max_correspondences=30/700).
Defaults unchanged => byte-identical. TPS + find-optimal-site kept (validated
on Vaishnavi: median 0.08px).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
plot_merge_example / fast_merge_example gain local_refinement + warp_kwargs and
apply refine_local_warp to the affine prediction, mirroring merge_sbs_phenotype,
so the notebook match preview reflects the levers an operator sets. Notebook-only
helper; defaults None => unchanged.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@mat10d mat10d merged commit 073fe7a into main Jul 10, 2026
3 checks passed
@mat10d mat10d deleted the merge-fast-path-levers branch July 10, 2026 15:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant