X-Git-Url: https://git.nihav.org/?a=blobdiff_plain;f=nihav-codec-support%2Fsrc%2Fvq%2Fgeneric_elbg.rs;h=2dfed5bf9f08496f272508064551ef014fdcd102;hb=f808017ea8cd6a3a5e6964d7e4467672a6c74245;hp=b2c838dc24236cfc15b30e13e4888ffd5b535ef9;hpb=971ae3066382f416b074c24df6b3213431856b81;p=nihav.git diff --git a/nihav-codec-support/src/vq/generic_elbg.rs b/nihav-codec-support/src/vq/generic_elbg.rs index b2c838d..2dfed5b 100644 --- a/nihav-codec-support/src/vq/generic_elbg.rs +++ b/nihav-codec-support/src/vq/generic_elbg.rs @@ -51,12 +51,11 @@ impl> Cluster { self.dist += u64::from(self.centroid.dist(entry.val)) * entry.count; } fn calc_centroid(&mut self) { - self.centroid = self.sum.get_centroid(); + if self.count > 0 { + self.centroid = self.sum.get_centroid(); + } } fn calc_dist(&mut self) { - if self.count != 0 { - self.dist = (self.dist + self.count / 2) / self.count; - } } } @@ -149,9 +148,9 @@ impl> ELBG { clu1.calc_dist(); clu0.dist + clu1.dist } - pub fn quantise(&mut self, src: &[T], dst: &mut [T]) { + pub fn quantise(&mut self, src: &[T], dst: &mut [T]) -> usize { if src.len() < 1 || dst.len() != self.clusters.len() { - return; + return 0; } let mut old_cb = vec![T::default(); self.clusters.len()]; let mut prev_dist = std::u64::MAX; @@ -177,17 +176,27 @@ impl> ELBG { entries.push(Entry { val: lastval, count: run }); drop(elements); + let mut cw_count = 0; let mut low_u: Vec = Vec::with_capacity(self.clusters.len()); let mut high_u: Vec = Vec::with_capacity(self.clusters.len()); let mut rng = RNG::new(); let mut iterations = 0usize; let mut do_elbg_step = true; - while (iterations < 20) && (dist < prev_dist - prev_dist / 1000) { + while (iterations < 20) && (dist < prev_dist - prev_dist / 100) { prev_dist = dist; - for i in 0..dst.len() { - old_cb[i] = self.clusters[i].centroid; - self.clusters[i].reset(); + + cw_count = 0; + for cluster in self.clusters.iter() { + if cluster.count == 0 { + continue; + } + old_cb[cw_count] = cluster.centroid; + cw_count += 1; } + for cluster in self.clusters.iter_mut() { + cluster.reset(); + } + // put points into the nearest clusters indices.truncate(0); for entry in entries.iter() { @@ -280,10 +289,16 @@ impl> ELBG { iterations += 1; } if dist < prev_dist { - for i in 0..dst.len() { - old_cb[i] = self.clusters[i].centroid; + cw_count = 0; + for cluster in self.clusters.iter() { + if cluster.count == 0 { + continue; + } + old_cb[cw_count] = cluster.centroid; + cw_count += 1; } } dst.copy_from_slice(&old_cb); + cw_count } }