diff options
| author | Pietro Albini <pietro@pietroalbini.org> | 2018-10-29 09:47:45 +0100 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2018-10-29 09:47:45 +0100 |
| commit | 97ff2d6ab1bea79c7ff4ae60a8ab600ce8b82c8e (patch) | |
| tree | 47402e0fc7d82c9fa26bffa7a69653b4ae770543 /src | |
| parent | 4e88b7363b7858960ccfd87326ece9d00bf4d973 (diff) | |
| parent | eb637d26ba4652ea65ef58288af0697c32ebc503 (diff) | |
| download | rust-97ff2d6ab1bea79c7ff4ae60a8ab600ce8b82c8e.tar.gz rust-97ff2d6ab1bea79c7ff4ae60a8ab600ce8b82c8e.zip | |
Rollup merge of #55384 - nnethercote:better-integer_lit-float_lit, r=michaelwoerister
Avoid unnecessary allocations in `float_lit` and `integer_lit`. This commit avoids an allocation when parsing any float and integer literals that don't involved underscores. This reduces the number of allocations done for the `tuple-stress` benchmark by 10%, reducing its instruction count by just under 1%.
Diffstat (limited to 'src')
| -rw-r--r-- | src/libsyntax/parse/mod.rs | 23 |
1 files changed, 19 insertions, 4 deletions
diff --git a/src/libsyntax/parse/mod.rs b/src/libsyntax/parse/mod.rs index a4b8ab86f37..77a2ae6acf0 100644 --- a/src/libsyntax/parse/mod.rs +++ b/src/libsyntax/parse/mod.rs @@ -494,8 +494,17 @@ fn float_lit(s: &str, suffix: Option<Symbol>, diag: Option<(Span, &Handler)>) -> Option<ast::LitKind> { debug!("float_lit: {:?}, {:?}", s, suffix); // FIXME #2252: bounds checking float literals is deferred until trans - let s = s.chars().filter(|&c| c != '_').collect::<String>(); - filtered_float_lit(Symbol::intern(&s), suffix, diag) + + // Strip underscores without allocating a new String unless necessary. + let s2; + let s = if s.chars().any(|c| c == '_') { + s2 = s.chars().filter(|&c| c != '_').collect::<String>(); + &s2 + } else { + s + }; + + filtered_float_lit(Symbol::intern(s), suffix, diag) } /// Parse a string representing a byte literal into its final form. Similar to `char_lit` @@ -591,8 +600,14 @@ fn integer_lit(s: &str, suffix: Option<Symbol>, diag: Option<(Span, &Handler)>) -> Option<ast::LitKind> { // s can only be ascii, byte indexing is fine - let s2 = s.chars().filter(|&c| c != '_').collect::<String>(); - let mut s = &s2[..]; + // Strip underscores without allocating a new String unless necessary. + let s2; + let mut s = if s.chars().any(|c| c == '_') { + s2 = s.chars().filter(|&c| c != '_').collect::<String>(); + &s2 + } else { + s + }; debug!("integer_lit: {}, {:?}", s, suffix); |
