From ff200c634549ce0004c954f5f8e5d3f7630c304f Mon Sep 17 00:00:00 2001 From: David Szotten Date: Mon, 31 Jul 2023 21:51:48 +0100 Subject: [PATCH] avoid some allocations --- crates/ruff_python_parser/src/string.rs | 30 ++++++++++++++----------- 1 file changed, 17 insertions(+), 13 deletions(-) diff --git a/crates/ruff_python_parser/src/string.rs b/crates/ruff_python_parser/src/string.rs index ec0e733e41c8c..5d212c3a457ad 100644 --- a/crates/ruff_python_parser/src/string.rs +++ b/crates/ruff_python_parser/src/string.rs @@ -182,11 +182,15 @@ impl<'a> StringParser<'a> { }; let mut expression = String::new(); + // for self-documenting strings we also store the `=` and any trailing space inside + // expression (because we want to combine it with any trailing spaces before the equal + // sign). the expression_length is the length of the actual expression part that we pass to + // `parse_fstring_expr` + let mut expression_length = 0; let mut spec = None; let mut delimiters = Vec::new(); let mut conversion = ConversionFlag::None; let mut self_documenting = false; - let mut trailing_seq = String::new(); let start_location = self.get_pos(); assert_eq!(self.next_char(), Some('{')); @@ -230,7 +234,8 @@ impl<'a> StringParser<'a> { // match a python 3.8 self documenting expression // format '{' PYTHON_EXPRESSION '=' FORMAT_SPECIFIER? '}' '=' if self.peek() != Some('=') && delimiters.is_empty() => { - trailing_seq.push('='); + expression_length = expression.len(); + expression.push(ch); self_documenting = true; } @@ -306,21 +311,22 @@ impl<'a> StringParser<'a> { let ret = if self_documenting { let value = - parse_fstring_expr(&expression, start_location).map_err(|e| { - FStringError::new( - InvalidExpression(Box::new(e.error)), - start_location, - ) - })?; + parse_fstring_expr(&expression[..expression_length], start_location) + .map_err(|e| { + FStringError::new( + InvalidExpression(Box::new(e.error)), + start_location, + ) + })?; let leading = &expression[..usize::from(value.range().start() - start_location) - 1]; - let before_eq = + let trailing = &expression[usize::from(value.range().end() - start_location) - 1..]; vec![Expr::from(ast::ExprFormattedValue { value: Box::new(value), debug_text: Some(ast::DebugText { leading: leading.to_string(), - trailing: format!("{before_eq}{trailing_seq}"), + trailing: trailing.to_string(), }), conversion, format_spec: spec, @@ -358,9 +364,7 @@ impl<'a> StringParser<'a> { } } } - ' ' if self_documenting => { - trailing_seq.push(ch); - } + ' ' if self_documenting => expression.push(ch), '\\' => return Err(FStringError::new(UnterminatedString, self.get_pos()).into()), _ => { if self_documenting {