Allow units to contain nubers after a caret

This commit is contained in:
Juhani Krekelä 2023-05-29 21:48:45 +03:00
parent fbbafcd2ec
commit 5335e141a4
1 changed files with 38 additions and 6 deletions

View File

@ -131,7 +131,7 @@ enum Token {
enum TokState { enum TokState {
Neutral, Neutral,
Number, Number,
Unit, Unit(bool),
} }
fn tokenize(input: &str) -> Vec<Token> { fn tokenize(input: &str) -> Vec<Token> {
@ -147,7 +147,7 @@ fn tokenize(input: &str) -> Vec<Token> {
state = TokState::Number; state = TokState::Number;
} else if !c.is_whitespace() { } else if !c.is_whitespace() {
token.push(c); token.push(c);
state = TokState::Unit; state = TokState::Unit(false);
} }
} }
TokState::Number => { TokState::Number => {
@ -157,17 +157,23 @@ fn tokenize(input: &str) -> Vec<Token> {
token.push(c); token.push(c);
} else { } else {
tokens.push(Token::Number(token.trim().to_string())); tokens.push(Token::Number(token.trim().to_string()));
state = TokState::Unit; state = TokState::Unit(false);
token = String::new(); token = String::new();
token.push(c); token.push(c);
} }
} }
TokState::Unit => { TokState::Unit(after_caret) => {
if c.is_ascii_digit() || c == '-' { if !after_caret && (c.is_ascii_digit() || c == '-') {
tokens.push(Token::Unit(token.trim().to_string())); tokens.push(Token::Unit(token.trim().to_string()));
state = TokState::Number; state = TokState::Number;
token = String::new(); token = String::new();
token.push(c); token.push(c);
} else if c == '^' {
token.push(c);
state = TokState::Unit(true);
} else if c.is_whitespace() {
token.push(c);
state = TokState::Unit(false);
} else { } else {
token.push(c); token.push(c);
} }
@ -178,7 +184,7 @@ fn tokenize(input: &str) -> Vec<Token> {
match state { match state {
TokState::Neutral => { assert!(token.len() == 0); } TokState::Neutral => { assert!(token.len() == 0); }
TokState::Number => { tokens.push(Token::Number(token.trim().to_string())); } TokState::Number => { tokens.push(Token::Number(token.trim().to_string())); }
TokState::Unit => { tokens.push(Token::Unit(token.trim().to_string())); } TokState::Unit(_) => { tokens.push(Token::Unit(token.trim().to_string())); }
} }
tokens tokens
@ -338,5 +344,31 @@ mod test {
Token::Number("2".to_string()), Token::Number("2".to_string()),
] ]
); );
assert_eq!(
tokenize("ft^2"),
vec![
Token::Unit("ft^2".to_string()),
]
);
assert_eq!(
tokenize("ft^22"),
vec![
Token::Unit("ft^22".to_string()),
]
);
assert_eq!(
tokenize("ft^2 2"),
vec![
Token::Unit("ft^2".to_string()),
Token::Number("2".to_string()),
]
);
assert_eq!(
tokenize("ft^2 s^-1 lb 2"),
vec![
Token::Unit("ft^2 s^-1 lb".to_string()),
Token::Number("2".to_string()),
]
);
} }
} }