Skip to contents

WHAT IT DOES: aligns each marker's distribution across batches, after checking that batch and biological group are separable enough for that to be meaningful.

Usage

correct_batch(
  tmat,
  batch,
  group = NULL,
  markers = NULL,
  max_cramers_v = NULL,
  force = FALSE,
  method = c("quantile", "cluster", "cytonorm"),
  cluster_k = 10L,
  seed = 42L,
  goal = c("group", "pooled")
)

Arguments

tmat

numeric matrix, cells x markers, already transformed

batch

batch label per cell

group

biological group per cell, for the confounding check

markers

markers to correct; defaults to all columns

max_cramers_v

refusal threshold, or NULL (default) for Cohen's "large" association; see cramers_v_limit().

force

proceed despite confounding

method

"quantile" for one map per marker over the whole file, or "cluster" (synonym "cytonorm") for one map per marker per cell type

cluster_k

number of cell-type clusters when method = "cluster"

seed

RNG seed for the clustering, so a run reproduces

goal

"group" or "pooled"; see above.

Value

list(tmat, cramers_v, corrected, markers, reason, method)

Details

TWO METHODS. "quantile" fits one map per marker over the whole file. "cluster" fits one map per marker per cell type, the idea CytoNorm is built on and what a whole-file map cannot do; see align_quantiles_by_cluster(). "cytonorm" is still accepted for "cluster", with a note: it is not the CytoNorm package, which learns its maps from anchor samples, and the name claimed otherwise.

THE GOAL. With group supplied and goal = "group", the default, each study group is aligned towards the mean of its quantiles over the batches every group was measured in, and nothing is corrected where no batch holds every group; see align_within_groups(). goal = "pooled" aligns every batch towards all samples together, which assumes the batches hold the same biology.

THE METHOD IS CHOSEN AFTER THE REFUSAL, NEVER BEFORE IT. A better alignment algorithm does not make a confounded design correctable. Where Cramer's V says batch and group are close to the same variable, both methods are refused identically, and force = TRUE remains the only way past.

WHAT IT REFUSES TO DO: correct when Cramer's V between batch and group exceeds max_cramers_v. At that point the two are close to the same variable, and any correction removes the effect being looked for. Passing force = TRUE proceeds and records the decision in the returned object so it reaches the run manifest.

This is descriptive of intensity only. It does not touch the gate hierarchy, which is derived per sample and is already batch-local by construction.