Added Integer Literal Parser

1. Added Integer Literal Parser
2. Removed Unused imports.
3. Fixed issues reported by Clippy
This commit is contained in:
Ishan Jain 2019-09-13 01:08:09 +05:30
parent 2863ad8aa4
commit 631c2d8b1a
4 changed files with 49 additions and 15 deletions

View File

@ -263,7 +263,7 @@ fn lookup_ident(ident: &str) -> Token {
#[cfg(test)]
mod tests {
use super::{Lexer, Literal, Token, TokenType};
use super::{Lexer, Token, TokenType};
use std::collections::HashMap;
#[test]

View File

@ -33,7 +33,7 @@ impl Let {
}
let literal = String::try_from(parser.current_token.clone().unwrap().value.unwrap())?;
let name = Identifier::new(Token::new(TokenType::Let), &literal);
let name = Identifier::new(Token::new(TokenType::Let), literal.into());
if !parser.expect_peek(Token::new(TokenType::Assign)) {
return Err(ParseError::new("expected =, Could not find it"));
@ -58,8 +58,8 @@ impl Return {
Return {
return_value: Expression::Ident(Identifier::new(
Token::new(TokenType::Return),
"return",
)), //TODO FIX THIS
"return".into(),
)),
}
}
@ -72,6 +72,10 @@ impl Return {
}
}
// Identifier is used to represent variable names and other user created identifiers.
// `Literal` can be an int as well. So, Identifier can be a Integer Literal
// The wording sounds a little confusing, maybe?
// TODO: possible @refactor
#[derive(Debug, PartialEq)]
pub struct Identifier {
name: Token,
@ -79,11 +83,8 @@ pub struct Identifier {
}
impl Identifier {
pub fn new(token: Token, name: &str) -> Identifier {
Identifier {
name: token,
value: name.into(),
}
pub fn new(name: Token, value: Literal) -> Identifier {
Identifier { name, value }
}
}

View File

@ -39,6 +39,7 @@ impl<'a> Parser<'a> {
prefix_parse_fns,
};
parser.register_prefix_fn(TokenType::Ident, Parser::parse_identifier);
parser.register_prefix_fn(TokenType::Int, Parser::parse_integer_literal);
parser
}
@ -59,7 +60,10 @@ impl<'a> Parser<'a> {
}
}
fn parse_expression(&mut self, priority: ExpressionPriority) -> Result<Expression, ParseError> {
fn parse_expression(
&mut self,
_priority: ExpressionPriority,
) -> Result<Expression, ParseError> {
let current_token = if let Some(token) = &self.current_token {
token
} else {
@ -83,7 +87,16 @@ impl<'a> Parser<'a> {
let ct = parser.current_token.clone().unwrap();
Ok(Expression::Ident(Identifier::new(
ct.clone(), // TODO: Correction needed, Can be a source of subtle error in some cases
&String::try_from(ct.value.unwrap())?,
String::try_from(ct.value.unwrap())?.into(),
)))
}
fn parse_integer_literal(parser: &mut Parser) -> Result<Expression, ParseError> {
let v = parser.current_token.clone().unwrap();
Ok(Expression::Ident(Identifier::new(
v.clone(),
v.value.unwrap(),
)))
}

View File

@ -46,7 +46,7 @@ mod tests {
let expected_out = Program {
statements: vec![
Statement::Let(Let::new(
Identifier::new(Token::new(TokenType::Let), "yr"),
Identifier::new(Token::new(TokenType::Let), "yr".into()),
None
// Some(Expression::Ident(Identifier::new(
// Token::new(TokenType::Let),
@ -54,7 +54,7 @@ mod tests {
// ))),
)),
Statement::Let(Let::new(
Identifier::new(Token::new(TokenType::Let), "qq"),
Identifier::new(Token::new(TokenType::Let), "qq".into()),
None
// Some(Expression::Ident(Identifier::new(
// Token::new(TokenType::Let),
@ -62,7 +62,7 @@ mod tests {
// ))),
)),
Statement::Let(Let::new(
Identifier::new(Token::new(TokenType::Let), "foobar"),
Identifier::new(Token::new(TokenType::Let), "foobar".into()),
None
// Some(Expression::Ident(Identifier::new(
// Token::new(TokenType::Let),
@ -103,7 +103,7 @@ mod tests {
Some(Token::with_value(TokenType::Ident, "foobar".into())),
Expression::Ident(Identifier::new(
Token::with_value(TokenType::Ident, "foobar".into()),
"foobar",
"foobar".into(),
)),
))],
};
@ -112,4 +112,24 @@ mod tests {
assert_eq!(as_tree.statements.len(), 1);
assert_eq!(as_tree, expected_out);
}
#[test]
fn integer_literal_expression() {
let ip = "5;";
let lexer = Lexer::new(ip);
let as_tree = Program::parse(lexer);
let expected_out = Program {
statements: vec![Statement::ExpressionStatement(ExpressionStatement::new(
Some(Token::with_value(TokenType::Int, 5.into())),
Expression::Ident(Identifier::new(
Token::with_value(TokenType::Int, 5.into()),
5.into(),
)),
))],
};
assert_eq!(as_tree.statements.len(), 1);
assert_eq!(as_tree, expected_out);
}
}