pub struct ExprMatrix { /* private fields */ }Expand description
An expression matrix with named rows (features/genes) and columns (samples).
Element (row i, col j) is stored at data[i * ncol + j]. Missing values
are represented as f64::NAN (the analog of R’s NA).
Implementations§
Source§impl ExprMatrix
impl ExprMatrix
Sourcepub fn new(
row_names: Vec<String>,
col_names: Vec<String>,
data: Vec<f64>,
) -> Self
pub fn new( row_names: Vec<String>, col_names: Vec<String>, data: Vec<f64>, ) -> Self
Build a matrix from row names, column names, and row-major data.
Panics if data.len() != row_names.len() * col_names.len().
Examples found in repository?
examples/quickstart.rs (line 39)
10fn main() {
11 // 6 genes (rows) x 3 samples (cols), log2-scale expression, stored row-major.
12 // Five are MCP-counter markers; GAPDH is a non-marker housekeeping gene and
13 // is ignored, exactly as in R (markers are matched by name against the
14 // bundled signature).
15 let genes = vec![
16 "CD3D".to_string(), // T cells
17 "CD28".to_string(), // T cells
18 "CD8B".to_string(), // CD8 T cells
19 "CD19".to_string(), // B lineage
20 "CD79A".to_string(), // B lineage
21 "GAPDH".to_string(), // not a marker -> ignored
22 ];
23 let samples = vec![
24 "tumor_A".to_string(),
25 "tumor_B".to_string(),
26 "normal".to_string(),
27 ];
28 #[rustfmt::skip]
29 let data = vec![
30 // tumor_A tumor_B normal
31 8.1, 7.4, 2.0, // CD3D
32 7.6, 7.1, 1.8, // CD28
33 6.9, 6.2, 1.5, // CD8B
34 4.2, 8.3, 2.1, // CD19
35 4.0, 8.0, 1.9, // CD79A
36 11.0, 11.1, 11.0, // GAPDH (flat housekeeping)
37 ];
38
39 let expr = ExprMatrix::new(genes, samples, data);
40 let result = mcp_counter(&expr, FeaturesType::HugoSymbols);
41
42 // Each score is the mean of a population's present markers. Populations with
43 // no present markers are dropped (as in R); the rest appear in MCP-counter's
44 // signature order: T cells, CD8 T cells, B lineage.
45 print!("{:<14}", "population");
46 for s in &result.samples {
47 print!("{s:>10}");
48 }
49 println!();
50 for (p, pop) in result.populations.iter().enumerate() {
51 print!("{pop:<14}");
52 for s in 0..result.samples.len() {
53 print!("{:>10.3}", result.score(p, s));
54 }
55 println!();
56 }
57}Sourcepub fn nrow(&self) -> usize
pub fn nrow(&self) -> usize
Number of rows (features).
Examples found in repository?
examples/parity_realdata.rs (line 84)
78fn main() {
79 let dir = PathBuf::from(DATA_DIR);
80
81 // --- MCP-counter on human racle (HUGO symbols) ---
82 let mcp_expr = read_tsv_matrix(&read_dump(&dir.join("mcp_real_input.tsv")));
83 let mcp_exp = read_dump(&dir.join("mcp_real_expected.tsv"));
84 let mcp_genes = mcp_expr.nrow();
85 let mcp_res = mcp_counter(&mcp_expr, FeaturesType::HugoSymbols);
86 let mcp_worst = worst_rel_err(&mcp_res, &mcp_exp);
87
88 // --- mMCP-counter on mouse petitprez (Gene.Symbol, GCRm39) ---
89 let mmcp_expr = read_tsv_matrix(&read_dump(&dir.join("mmcp_real_input.tsv")));
90 let mmcp_exp = read_dump(&dir.join("mmcp_real_expected.tsv"));
91 let mmcp_genes = mmcp_expr.nrow();
92 let mmcp_res = mmcp_counter(
93 &mmcp_expr,
94 MurineFeaturesType::GeneSymbol,
95 GenomeVersion::GCRm39,
96 );
97 let mmcp_worst = worst_rel_err(&mmcp_res, &mmcp_exp);
98
99 // --- report ---
100 println!("Real-data parity vs R reference estimators (R 4.6.0)\n");
101 println!(
102 " {:<13} {:<18} {:>7} {:>4} pops {:>3} samples worst rel err {:>9}",
103 "MCP-counter",
104 "dataset_racle",
105 mcp_genes,
106 mcp_res.populations.len(),
107 mcp_res.samples.len(),
108 format!("{mcp_worst:e}"),
109 );
110 println!(
111 " {:<13} {:<18} {:>7} {:>4} pops {:>3} samples worst rel err {:>9}",
112 "mMCP-counter",
113 "dataset_petitprez",
114 mmcp_genes,
115 mmcp_res.populations.len(),
116 mmcp_res.samples.len(),
117 format!("{mmcp_worst:e}"),
118 );
119
120 // --- aggregate metrics (raw matrices are never committed) ---
121 let json = format!(
122 r#"{{
123 "description": "Real-data parity: mcpcounter-rust vs R reference estimators (R 4.6.0)",
124 "regenerate": "Rscript benchmarks/parity_realdata.R && cargo run --example parity_realdata",
125 "threshold_relative_error": {threshold},
126 "datasets": [
127 {{
128 "method": "MCP-counter",
129 "dataset": "dataset_racle",
130 "organism": "human",
131 "citation": "Racle et al. 2017, eLife 6:e26476",
132 "features_type": "HUGO_symbols",
133 "input_genes": {mcp_genes},
134 "populations": {mcp_pops},
135 "samples": {mcp_samples},
136 "worst_relative_error": {mcp_worst}
137 }},
138 {{
139 "method": "mMCP-counter",
140 "dataset": "dataset_petitprez",
141 "organism": "mouse",
142 "citation": "Petitprez et al. 2020, Genome Med 12:86",
143 "features_type": "Gene.Symbol",
144 "genome_version": "GCRm39",
145 "input_genes": {mmcp_genes},
146 "populations": {mmcp_pops},
147 "samples": {mmcp_samples},
148 "worst_relative_error": {mmcp_worst}
149 }}
150 ]
151}}
152"#,
153 threshold = THRESHOLD,
154 mcp_genes = mcp_genes,
155 mcp_pops = mcp_res.populations.len(),
156 mcp_samples = mcp_res.samples.len(),
157 mcp_worst = mcp_worst,
158 mmcp_genes = mmcp_genes,
159 mmcp_pops = mmcp_res.populations.len(),
160 mmcp_samples = mmcp_res.samples.len(),
161 mmcp_worst = mmcp_worst,
162 );
163 if let Err(e) = fs::write(RESULTS_PATH, &json) {
164 eprintln!("warning: could not write {RESULTS_PATH}: {e}");
165 } else {
166 println!("\nwrote {RESULTS_PATH}");
167 }
168
169 // --- gate ---
170 let failed = mcp_worst >= THRESHOLD || mmcp_worst >= THRESHOLD;
171 if failed {
172 eprintln!("\nFAIL: worst relative error exceeds {THRESHOLD:e}");
173 process::exit(1);
174 }
175 println!("\nOK: both methods within {THRESHOLD:e} relative error of R");
176}Sourcepub fn row_names(&self) -> &[String]
pub fn row_names(&self) -> &[String]
Row (feature) names.
Examples found in repository?
examples/parity_realdata.rs (line 48)
44fn worst_rel_err(res: &DeconvResult, expected_tsv: &str) -> f64 {
45 let exp = read_tsv_matrix(expected_tsv); // rows = populations, cols = samples
46 assert_eq!(
47 res.populations,
48 exp.row_names(),
49 "population order mismatch"
50 );
51 assert_eq!(res.samples, exp.col_names(), "sample order mismatch");
52
53 let mut worst = 0.0f64;
54 for i in 0..res.populations.len() {
55 for j in 0..res.samples.len() {
56 let got = res.score(i, j);
57 let want = exp.get(i, j);
58 let rel = (got - want).abs() / want.abs().max(1e-300);
59 worst = worst.max(rel);
60 }
61 }
62 worst
63}Sourcepub fn col_names(&self) -> &[String]
pub fn col_names(&self) -> &[String]
Column (sample) names.
Examples found in repository?
examples/parity_realdata.rs (line 51)
44fn worst_rel_err(res: &DeconvResult, expected_tsv: &str) -> f64 {
45 let exp = read_tsv_matrix(expected_tsv); // rows = populations, cols = samples
46 assert_eq!(
47 res.populations,
48 exp.row_names(),
49 "population order mismatch"
50 );
51 assert_eq!(res.samples, exp.col_names(), "sample order mismatch");
52
53 let mut worst = 0.0f64;
54 for i in 0..res.populations.len() {
55 for j in 0..res.samples.len() {
56 let got = res.score(i, j);
57 let want = exp.get(i, j);
58 let rel = (got - want).abs() / want.abs().max(1e-300);
59 worst = worst.max(rel);
60 }
61 }
62 worst
63}Sourcepub fn row_of(&self, name: &str) -> Option<usize>
pub fn row_of(&self, name: &str) -> Option<usize>
First row index for a feature name, if present.
Sourcepub fn get(&self, row: usize, col: usize) -> f64
pub fn get(&self, row: usize, col: usize) -> f64
Value at (row, col).
Examples found in repository?
examples/parity_realdata.rs (line 57)
44fn worst_rel_err(res: &DeconvResult, expected_tsv: &str) -> f64 {
45 let exp = read_tsv_matrix(expected_tsv); // rows = populations, cols = samples
46 assert_eq!(
47 res.populations,
48 exp.row_names(),
49 "population order mismatch"
50 );
51 assert_eq!(res.samples, exp.col_names(), "sample order mismatch");
52
53 let mut worst = 0.0f64;
54 for i in 0..res.populations.len() {
55 for j in 0..res.samples.len() {
56 let got = res.score(i, j);
57 let want = exp.get(i, j);
58 let rel = (got - want).abs() / want.abs().max(1e-300);
59 worst = worst.max(rel);
60 }
61 }
62 worst
63}Trait Implementations§
Source§impl Clone for ExprMatrix
impl Clone for ExprMatrix
Source§fn clone(&self) -> ExprMatrix
fn clone(&self) -> ExprMatrix
Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
Performs copy-assignment from
source. Read moreAuto Trait Implementations§
impl Freeze for ExprMatrix
impl RefUnwindSafe for ExprMatrix
impl Send for ExprMatrix
impl Sync for ExprMatrix
impl Unpin for ExprMatrix
impl UnsafeUnpin for ExprMatrix
impl UnwindSafe for ExprMatrix
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Mutably borrows from an owned value. Read more