Skip to content

Add experimental recursive iCanClean - #58

Draft
snesmaeili wants to merge 2 commits into
mainfrom
codex/recursive-icanclean
Draft

Add experimental recursive iCanClean#58
snesmaeili wants to merge 2 commits into
mainfrom
codex/recursive-icanclean

Conversation

@snesmaeili

@snesmaeili snesmaeili commented Aug 1, 2026

Copy link
Copy Markdown
Contributor

Pull Request

Description

This draft adds an explicitly experimental RecursiveICanClean estimator. It is a new online composition built from recursive joint moments, regularized rank-aware CCA, and the published iCanClean component-selection and least-squares subtraction rule.

The implementation provides:

  • causal streaming with update-after by default and an explicit update-before mode
  • adaptive and frozen operation, contamination masks, warm-up and update intervals in samples or physical time
  • faithful X, Y, and both-basis iCanClean behavior, including rereferencing
  • MNE Raw and NumPy inputs with locked representation, channel geometry, units, and timeline checks
  • rank, convergence, causality, operator-change, and state diagnostics
  • reset plus strict, lossless, canonical JSON checkpoint/replay with schema and checksum validation
  • transactional state loading that preserves the last valid model when validation fails

The documentation makes the evidence boundary explicit: the published fixed/moving-window iCanClean results do not validate this recursive implementation. The 2023 paper identifies recursive CCA as future work; this PR does not claim author-code parity or real-data effectiveness. transform is frozen, and held-out effectiveness evaluation must use calibration data disjoint from evaluation data.

Related Issue

Builds on the batch iCanClean API introduced for #25. This recursive extension comes from the evidence-aware roadmap and intentionally remains a draft pending maintainer discussion and empirical validation.

Type of Change

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Documentation update

Verification

  • Python 3.10 and 3.12 recursive and batch iCanClean tests: 174 passed on each
  • Python 3.12 full suite: 1,046 passed, 20 expected optional skips
  • Local branch coverage for recursive.py: 99% (803/806 executable lines and 371/374 branches covered; Codecov-like full-line estimate 99.26%)
  • Ruff and all pre-commit hooks pass
  • Tests cover batch bridges for X, Y, both, and rereferencing; chunk invariance; physical-unit scaling; causality; MNE metadata and timeline enforcement; contamination gates; checkpoint validation; and exact state replay
  • The recursive documentation page renders warning-free

A repository-wide Sphinx -W run still encounters one pre-existing SmoothingBias cross-reference error. A full gallery build additionally encountered two external ZapLine data-download HTTP 503 responses. Neither originates in this change.

Remaining evidence before promotion

This PR establishes implementation, invariant, and synthetic support only. Independent recursive-CCA parity, real phantom/human effectiveness, neural-preservation, sustained-contamination, and latency/memory campaigns remain outstanding.

Checklist

  • My code follows the code style of this project (ruff check ., ruff format .)
  • I have added tests that prove my fix is effective or that my feature works
  • I have run the full test suite and all tests pass
  • I have updated the documentation accordingly (make -C docs html builds without warnings)
  • I have added a changelog fragment

Draft only: do not merge or mark ready.

@codecov

codecov Bot commented Aug 1, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 99.25651% with 6 lines in your changes missing coverage. Please review.
✅ Project coverage is 96.37%. Comparing base (e84d8d0) to head (fdb37d7).

Files with missing lines Patch % Lines
mne_denoise/icanclean/recursive.py 99.25% 3 Missing and 3 partials ⚠️
Additional details and impacted files

Impacted file tree graph

@@            Coverage Diff             @@
##             main      #58      +/-   ##
==========================================
+ Coverage   96.08%   96.37%   +0.29%     
==========================================
  Files          65       66       +1     
  Lines        8170     8977     +807     
  Branches     1420     1607     +187     
==========================================
+ Hits         7850     8652     +802     
- Misses        152      155       +3     
- Partials      168      170       +2     
Flag Coverage Δ
unittests 96.37% <99.25%> (+0.29%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

Files with missing lines Coverage Δ
mne_denoise/icanclean/__init__.py 100.00% <100.00%> (ø)
mne_denoise/icanclean/recursive.py 99.25% <99.25%> (ø)

... and 1 file with indirect coverage changes

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

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