Skip to content

Commit

Permalink
feat(interpreter): add or operator (#26)
Browse files Browse the repository at this point in the history
  • Loading branch information
vit0rr authored Nov 7, 2024
1 parent feafc37 commit 9d8b178
Show file tree
Hide file tree
Showing 8 changed files with 34 additions and 1 deletion.
5 changes: 4 additions & 1 deletion code.monkey
Original file line number Diff line number Diff line change
@@ -1 +1,4 @@
1 + 2
let LESS_THAN_OR_EQUAL = fn(x, y) {
return (x < y) || (x == y);
}
puts(LESS_THAN_OR_EQUAL(1, 2));
10 changes: 10 additions & 0 deletions evaluator/evaluator.go
Original file line number Diff line number Diff line change
Expand Up @@ -316,6 +316,9 @@ func evalInfixExpression(operator string, left, right object.Object) object.Obje
case operator == "!=":
return nativeBoolToBooleanObject(left != right)

case operator == "||":
return evalOrInfixExpression(left, right)

case left.Type() != right.Type():
return newError("type mismatch: %s %s %s", left.Type(), operator, right.Type())

Expand All @@ -324,6 +327,13 @@ func evalInfixExpression(operator string, left, right object.Object) object.Obje
}
}

func evalOrInfixExpression(left, right object.Object) object.Object {
leftVal := left.(*object.Boolean).Value
rightVal := right.(*object.Boolean).Value

return nativeBoolToBooleanObject(leftVal || rightVal)
}

func evalStringInfixExpression(operator string, left, right object.Object) object.Object {
switch operator {
case "+":
Expand Down
2 changes: 2 additions & 0 deletions evaluator/evaluator_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,8 @@ func TestEvalBooleanExpression(t *testing.T) {
{"(1 < 2) == false", false},
{"(1 > 2) == true", false},
{"(1 > 2) == false", true},
{"true || false", true},
{"(1 > 2) || (5 > 4)", true},
}

for _, tt := range tests {
Expand Down
8 changes: 8 additions & 0 deletions lexer/lexer.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,14 @@ func (l *Lexer) NextToken() token.Token {
} else {
tok = newToken(token.ASSIGN, l.ch)
}
case '|':
if l.peekChar() == '|' {
ch := l.ch
l.readChar()
tok = token.Token{Type: token.OR, Literal: string(ch) + string(l.ch)}
} else {
tok = newToken(token.ILLEGAL, l.ch)
}
case ';':
tok = newToken(token.SEMICOLON, l.ch)
case '(':
Expand Down
5 changes: 5 additions & 0 deletions lexer/lexer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ func TestNextToken(t *testing.T) {
"foo bar"
[1, 2];
{"foo": "bar"}
true || false;
// this is a comment
`

Expand Down Expand Up @@ -123,6 +124,10 @@ func TestNextToken(t *testing.T) {
{token.COLON, ":"},
{token.STRING, "bar"},
{token.RBRACE, "}"},
{token.TRUE, "true"},
{token.OR, "||"},
{token.FALSE, "false"},
{token.SEMICOLON, ";"},
{token.EOF, ""},
}

Expand Down
3 changes: 3 additions & 0 deletions parser/parser.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ const (
_ int = iota
LOWEST
EQUALS // ==
OR // ||
LESSGREATER // > or <
SUM // +
PRODUCT // *
Expand All @@ -26,6 +27,7 @@ var precedences = map[token.TokenType]int{
token.NOT_EQ: EQUALS,
token.LT: LESSGREATER,
token.GT: LESSGREATER,
token.OR: OR,
token.PLUS: SUM,
token.MINUS: SUM,
token.SLASH: PRODUCT,
Expand Down Expand Up @@ -86,6 +88,7 @@ func New(l *lexer.Lexer) *Parser {
p.registerInfix(token.ASTERISK, p.parseInfixExpression)
p.registerInfix(token.EQ, p.parseInfixExpression)
p.registerInfix(token.NOT_EQ, p.parseInfixExpression)
p.registerInfix(token.OR, p.parseInfixExpression)
p.registerInfix(token.LT, p.parseInfixExpression)
p.registerInfix(token.GT, p.parseInfixExpression)
p.registerInfix(token.LPAREN, p.parseCallExpression)
Expand Down
1 change: 1 addition & 0 deletions parser/parser_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -207,6 +207,7 @@ func TestParsingInfixExpressions(t *testing.T) {
{"5 < 5;", 5, "<", 5},
{"5 == 5;", 5, "==", 5},
{"5 != 5;", 5, "!=", 5},
{"true || false", true, "||", false},
}

for _, tt := range infixTests {
Expand Down
1 change: 1 addition & 0 deletions token/token.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ const (

EQ = "=="
NOT_EQ = "!="
OR = "||"

// Delimiters
COMMA = ","
Expand Down

0 comments on commit 9d8b178

Please sign in to comment.