From 40811151abf12dfd308223add0705a0776e51559 Mon Sep 17 00:00:00 2001 From: "Elf M. Sternberg" Date: Sun, 13 Nov 2022 12:33:34 -0800 Subject: [PATCH] The C and Rust versions are now comparable. The C and Rust versions are now comparable, with a memory-reuse and a memory-safe version for Rust. The memory-safe version is five times faster than the C version; the memory-reuse version (technically safe, but can panic under some very rare circumstances) is ten times faster. I suspect the reasons for he speedup are strictly in the `for()` loop in the C version for copying the string, where the Rust version probably uses memcpy() under the covers to transfer the short string into the destination. --- crates/squozen/docs/patprep/bench_patprep.c | 2 +- crates/squozen/src/prepare_pattern.rs | 18 +++++++++++++----- 2 files changed, 14 insertions(+), 6 deletions(-) diff --git a/crates/squozen/docs/patprep/bench_patprep.c b/crates/squozen/docs/patprep/bench_patprep.c index ab36738..37b033d 100644 --- a/crates/squozen/docs/patprep/bench_patprep.c +++ b/crates/squozen/docs/patprep/bench_patprep.c @@ -1,6 +1,6 @@ #include "patprep.h" -const int count = 5 * 1000 * 1000 * 1000; +const int count = 5 * 1000 * 1000 * 100; void main() { for (int i = 0; i <= count; i++) { diff --git a/crates/squozen/src/prepare_pattern.rs b/crates/squozen/src/prepare_pattern.rs index 6966372..77d021d 100644 --- a/crates/squozen/src/prepare_pattern.rs +++ b/crates/squozen/src/prepare_pattern.rs @@ -28,6 +28,12 @@ where } pub fn prepare_pattern(name: &[u8]) -> Vec { + let mut dest = Vec::with_capacity(116); + prepare_pattern_raw(name, &mut dest); + dest +} + +pub fn prepare_pattern_raw(name: &[u8], dest: &mut Vec) { let mut eol = name.len(); if eol == 0 { panic!("Library error - This function should never be called with an empty string.") @@ -43,10 +49,12 @@ pub fn prepare_pattern(name: &[u8]) -> Vec { } if eol == 0 { - return if GLOBCHARS.contains(&name[0]) { - vec![b'/'] + if GLOBCHARS.contains(&name[0]) { + dest.push(b'/'); + return; } else { - vec![name[0]] + dest.push(name[0]); + return; }; } @@ -57,9 +65,9 @@ pub fn prepare_pattern(name: &[u8]) -> Vec { start }; if start > eol { - vec![b'/'] + dest.push(b'/'); } else { - name[start..eol + 1].to_vec() + dest.extend_from_slice(&name[start..eol + 1]); } }