Add joint MAP hierarchical CT-AR Rasch slice (stacked on #976) - #982
Conversation
Introduce a Rust-owned jointly estimated longitudinal IRT kernel stacked on the #976 OLS/AR state layer: shared (mu, tau, lambda), elapsed-day OU transitions, measurement-information Wald state intervals, and honest estimand metadata. Multiple-membership u_h and GPU parity are excluded. Python remains marshalling-only. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com>
|
Important Review skippedAuto reviews are disabled on base/target branches other than the default branch. Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Plus Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
NumPy 2 no longer treats ndarray as a Sequence, so the hierarchical simulator now accepts both sequences and arrays. Empirical-scale helpers used only by unit tests are cfg(test) so the production lib stays clean. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com>
|
Bugbot is not enabled for your account, so this pull request was not reviewed. Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs. |
17bebdc
into
cursor/rust-longitudinal-state-4683
#1005) * feat: add Rust-owned longitudinal OLS and AR state layer Land a focused successor to #848 on live main: independent per-respondent OLS trends and caller-supplied discrete AR predictions, with honest estimand metadata, fail-closed worker joins, checked AR gaps, and scale-relative slope degeneracy. Number the decision ADR-0018 so it does not collide with main ADR-0015 or #948 ADRs 0016/0017. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * test: recover OLS parameters with valid respondent identifiers Use two-token snake_case respondent IDs and cover NumPy scalar observation conversion on the public longitudinal boundary. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * docs: index ADR-0016/0017 so the longitudinal PR stays merge-safe PR 948 already records Angoff delta-plot and Bradley-Terry MM. Carry those accepted ADRs in this branch so the index does not skip numbers and a later merge with the citation work does not drop them. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * Revert "docs: index ADR-0016/0017 so the longitudinal PR stays merge-safe" This reverts commit eafb302. * test: cover unused worker shards and real observation scalars Close the leftover llvm-cov paths in the longitudinal state engine: skip an unused worker chunk, test first-to-last sequence-span underflow as a helper, and recover an AR series that starts after a leading missing occasion. Accept Python int and NumPy integer scalars at the public boundary. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * ci: retrigger org CodeQL after GitHub API 503 The required default-setup Analyze (actions) job is still the 17:40 UTC init failure (feature-enablement HTTP 503). The repository CodeQL copy already passed on a later rerun. This integration cannot call `gh run rerun` (403, needs actions: write), so retrigger the stale org check without changing product code. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * Add joint MAP hierarchical CT-AR Rasch slice (stacked on #976) (#982) * Add joint MAP hierarchical continuous-time AR(1) Rasch slice. Introduce a Rust-owned jointly estimated longitudinal IRT kernel stacked on the #976 OLS/AR state layer: shared (mu, tau, lambda), elapsed-day OU transitions, measurement-information Wald state intervals, and honest estimand metadata. Multiple-membership u_h and GPU parity are excluded. Python remains marshalling-only. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * Accept NumPy intercept vectors and hide test-only scale helpers. NumPy 2 no longer treats ndarray as a Sequence, so the hierarchical simulator now accepts both sequences and arrays. Empirical-scale helpers used only by unit tests are cfg(test) so the production lib stays clean. Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> --------- Co-authored-by: Cursor Agent <cursoragent@cursor.com> Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> * test(longitudinal): align single-occasion fit error * test(multilevel): require longitudinal state binding registration * docs(architecture): keep proposed longitudinal ADRs non-shipped * fix(multilevel): bound simulator arrays before copying * docs(multilevel): distinguish OLS from discrete AR spacing * test(longitudinal): expose hostile execution-control callbacks * fix(longitudinal): harden execution-control boundary * chore(longitudinal): leave aggregate changelog to release serialization * fix(longitudinal): align bounded gradients and Hessian evidence * fix(longitudinal): enforce identified simulator controls * fix(longitudinal): bound raw inputs and diagonal intervals * fix(longitudinal): close current review boundary gaps * docs: keep ADR index unique and ordered --------- Co-authored-by: Cursor Agent <cursoragent@cursor.com> Co-authored-by: Seongho Bae <seonghobae@users.noreply.github.com> Co-authored-by: Claude <noreply@anthropic.com>
Dependency
This PR is stacked on #976 (
cursor/rust-longitudinal-state-4683). It must not be merged tomainuntil #976 lands. It does not relabel the #976 OLS / caller-supplied AR kernels as random effects.Duplicate check
Inspected open PRs/issues before starting, including #978, #979, and #981. No open PR implements jointly estimated hierarchical longitudinal IRT. #976 is the OLS/AR base; closed #848 is the same OLS/AR tree.
What this adds
Smallest scientifically valid jointly estimated longitudinal latent-state IRT slice:
Delta_ptis elapsed days from exact millisecond offsets.Honest labels:
estimand_scope = joint_map_hierarchical_ctar_raschtransition_kind = continuous_time_ar1_ouinterval_kind = wald_measurement_observed_informationpopulation_random_effects_estimated = True(sharedmu,tau; states shrunk towardmu)ar_coefficient_source = joint_mapmultiple_membership_estimated = Falsegpu_parity = FalseThis is joint MAP, not Fox & Glas Gibbs, not Jeon & Rabe-Hesketh adaptive quadrature, not independent OLS, and not caller-supplied discrete AR.
Exclusions (contracted)
u_h: not in this joint likelihood. Next step is a dedicated identification study combining Fox & Glas multilevel IRT with Browne et al. MMMC.Recovery honesty
Multi-seed tests recover known person-occasion states (RMSE / measurement-information Wald coverage) and the population mean. Joint MAP shrinks
tau. Short irregular series leavelambdaweakly identified; tests require a finite positive decay and unit-dayphiin(0, 1), plus irregular-gapphiordering, not tight unbiased-ML recovery oflambda.Docs
ADR-0019 (Proposed), doctoring, ARCHITECTURE, traceability, PRD-FR-061 / TRD-MLT-004–005, VV-SCI-008, CHANGELOG. APA 7th primary citations; journal PDFs are copyrighted so they are cited + linked + summarized, not attached.
Evidence on this head
cargo test --locked --manifest-path crates/mlsirm-core/Cargo.toml --lib longitudinal_irt: 11 passedcargo test --locked --workspace: passedcargo test --locked --manifest-path crates/fast-mlsirm-py/Cargo.toml: 9 passedpytesthierarchical IRT + longitudinal OLS/AR + loader + architecture/changelog/docs: 17 + supporting tests passedresolve_backend(auto) == rustfuzz_configharness: 8s bounded run completed without crashtest_marginal_gpu_agrees_with_cpu_loosely: skipped here (no Vulkan adapter). This slice adds no GPU kernel; CI gpu-smoke remains the MLSIRM path and must not be claimed from this environment.