Skip to content

Commit 175d860

Browse files
committed
Add SVD threshold based on frobenius norm diff wrt to true matrix
1 parent 802d7da commit 175d860

File tree

1 file changed

+16
-9
lines changed

1 file changed

+16
-9
lines changed

kifmm/src/fmm/field_translation/metadata/single_node.rs

+16-9
Original file line numberDiff line numberDiff line change
@@ -55,21 +55,28 @@ use crate::{
5555

5656
/// Compute the cutoff rank for an SVD decomposition of a matrix from its singular values
5757
/// using a specified `threshold` as a tolerance parameter
58-
pub fn find_cutoff_rank<T: Float + RlstScalar + Gemm>(
58+
pub(crate) fn find_cutoff_rank<T: Float + RlstScalar + Gemm>(
5959
singular_values: &[T],
6060
threshold: T,
61-
max_rank: usize,
61+
max_rank: usize
6262
) -> usize {
63+
6364
let len = singular_values.len().min(max_rank);
65+
let mut frob_k: Vec<T> = singular_values.iter()
66+
.rev() // Reverse order
67+
.map(|&x| x * x) // Square each element
68+
.scan(T::zero(), |acc, x| {
69+
*acc += x;
70+
Some(*acc)
71+
}) // Compute cumulative sum
72+
.map(<T as RlstScalar>::sqrt) // Take the square root
73+
.collect();
74+
75+
frob_k.reverse(); // Reverse back to original order
76+
frob_k.iter().position(|&x| x < threshold).unwrap_or(len - 1)
77+
}
6478

65-
for (i, &s) in singular_values.iter().take(len).enumerate() {
66-
if s <= threshold {
67-
return i;
68-
}
69-
}
7079

71-
len - 1
72-
}
7380
impl<Scalar, FieldTranslation> SourceTranslationMetadata
7481
for KiFmm<Scalar, Laplace3dKernel<Scalar>, FieldTranslation>
7582
where

0 commit comments

Comments
 (0)