Skip to content

Commit 8dd9145

Browse files
authored
Merge pull request #31 from ChanTsune/feature/performance-improvement
Improved performance by eliminating String creation by utilizing the original &str slice.
2 parents 5235bf4 + 68e74bc commit 8dd9145

File tree

1 file changed

+28
-8
lines changed

1 file changed

+28
-8
lines changed

src/parse.rs

+28-8
Original file line numberDiff line numberDiff line change
@@ -7,16 +7,12 @@ impl std::str::FromStr for ByteSize {
77
if let Ok(v) = value.parse::<u64>() {
88
return Ok(Self(v));
99
}
10-
let number: String = value
11-
.chars()
12-
.take_while(|c| c.is_ascii_digit() || c == &'.')
13-
.collect();
10+
let number = take_while(value, |c| c.is_ascii_digit() || c == '.');
1411
match number.parse::<f64>() {
1512
Ok(v) => {
16-
let suffix: String = value
17-
.chars()
18-
.skip_while(|c| c.is_whitespace() || c.is_ascii_digit() || c == &'.')
19-
.collect();
13+
let suffix = skip_while(value, |c| {
14+
c.is_whitespace() || c.is_ascii_digit() || c == '.'
15+
});
2016
match suffix.parse::<Unit>() {
2117
Ok(u) => Ok(Self((v * u) as u64)),
2218
Err(error) => Err(format!(
@@ -33,6 +29,30 @@ impl std::str::FromStr for ByteSize {
3329
}
3430
}
3531

32+
fn take_while<P>(s: &str, mut predicate: P) -> &str
33+
where
34+
P: FnMut(char) -> bool,
35+
{
36+
let offset = s
37+
.chars()
38+
.take_while(|ch| predicate(*ch))
39+
.map(|ch| ch.len_utf8())
40+
.sum();
41+
&s[..offset]
42+
}
43+
44+
fn skip_while<P>(s: &str, mut predicate: P) -> &str
45+
where
46+
P: FnMut(char) -> bool,
47+
{
48+
let offset: usize = s
49+
.chars()
50+
.skip_while(|ch| predicate(*ch))
51+
.map(|ch| ch.len_utf8())
52+
.sum();
53+
&s[(s.len() - offset)..]
54+
}
55+
3656
enum Unit {
3757
Byte,
3858
// power of tens

0 commit comments

Comments
 (0)