perf(mesh): memoise the whole-container decode
Filtering after the assignment made every subset query a full decode (~15s on a 50MB container). full_decode_cached memoises it per container -- fingerprint is length plus three sampled 4KB windows, keyed with min_consistency, last four kept. Decoding five ships from Stage_S02 in turn: 10.5s for the first, then 48us-1.4ms. A stage now costs one decode rather than one per ship. Ten suites green, viewer builds, and a spot-checked resource still lands on the same offset. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
22
crates/sylpheed-formats/examples/bench_ships.rs
Normal file
22
crates/sylpheed-formats/examples/bench_ships.rs
Normal file
@@ -0,0 +1,22 @@
|
||||
//! Time repeated per-ship decodes of one container, as the viewer does.
|
||||
use std::collections::HashSet;
|
||||
use std::time::Instant;
|
||||
use sylpheed_formats::mesh::Xbg7Model;
|
||||
use sylpheed_formats::ship::{is_base_part, ship_id_of};
|
||||
fn main() {
|
||||
let a: Vec<String> = std::env::args().collect();
|
||||
let bytes = std::fs::read(&a[1]).unwrap();
|
||||
let names = sylpheed_formats::mesh::xbg7_resource_names(&bytes);
|
||||
let ids: Vec<String> = {
|
||||
let mut v: Vec<String> = names.iter().filter(|n| is_base_part(n))
|
||||
.filter_map(|n| ship_id_of(n).map(|s| s.to_string())).collect();
|
||||
v.sort(); v.dedup(); v.truncate(5); v
|
||||
};
|
||||
for id in &ids {
|
||||
let want: HashSet<String> = names.iter()
|
||||
.filter(|n| ship_id_of(n) == Some(id.as_str())).cloned().collect();
|
||||
let t = Instant::now();
|
||||
let got = Xbg7Model::models_named(&bytes, &want, &|| false);
|
||||
println!("{id}: {} models in {:?}", got.len(), t.elapsed());
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user