add nil literal
This commit is contained in:
parent
e8d4bc98ae
commit
5daf4f9aa2
@ -136,6 +136,10 @@ func (c *compiler) compileExpression(expr parser.Expression) {
|
|||||||
constIndex := c.addConstant(e.Value)
|
constIndex := c.addConstant(e.Value)
|
||||||
c.emit(types.OpConstant, constIndex)
|
c.emit(types.OpConstant, constIndex)
|
||||||
|
|
||||||
|
case *parser.NilLiteral:
|
||||||
|
constIndex := c.addConstant(nil)
|
||||||
|
c.emit(types.OpConstant, constIndex)
|
||||||
|
|
||||||
case *parser.Identifier:
|
case *parser.Identifier:
|
||||||
nameIndex := c.addConstant(e.Value)
|
nameIndex := c.addConstant(e.Value)
|
||||||
|
|
||||||
|
@ -37,6 +37,7 @@ const (
|
|||||||
TokenOr
|
TokenOr
|
||||||
TokenNot
|
TokenNot
|
||||||
TokenElseIf
|
TokenElseIf
|
||||||
|
TokenNil
|
||||||
)
|
)
|
||||||
|
|
||||||
type Token struct {
|
type Token struct {
|
||||||
@ -166,6 +167,8 @@ func (l *Lexer) NextToken() Token {
|
|||||||
tok.Type = TokenOr
|
tok.Type = TokenOr
|
||||||
case "not":
|
case "not":
|
||||||
tok.Type = TokenNot
|
tok.Type = TokenNot
|
||||||
|
case "nil":
|
||||||
|
tok.Type = TokenNil
|
||||||
default:
|
default:
|
||||||
tok.Type = TokenIdentifier
|
tok.Type = TokenIdentifier
|
||||||
}
|
}
|
||||||
|
@ -156,3 +156,10 @@ type BooleanLiteral struct {
|
|||||||
|
|
||||||
func (bl *BooleanLiteral) expressionNode() {}
|
func (bl *BooleanLiteral) expressionNode() {}
|
||||||
func (bl *BooleanLiteral) TokenLiteral() string { return bl.Token.Value }
|
func (bl *BooleanLiteral) TokenLiteral() string { return bl.Token.Value }
|
||||||
|
|
||||||
|
type NilLiteral struct {
|
||||||
|
Token lexer.Token
|
||||||
|
}
|
||||||
|
|
||||||
|
func (nl *NilLiteral) expressionNode() {}
|
||||||
|
func (nl *NilLiteral) TokenLiteral() string { return nl.Token.Value }
|
||||||
|
@ -74,6 +74,7 @@ func New(l *lexer.Lexer) *Parser {
|
|||||||
p.registerPrefix(lexer.TokenTrue, p.parseBooleanLiteral)
|
p.registerPrefix(lexer.TokenTrue, p.parseBooleanLiteral)
|
||||||
p.registerPrefix(lexer.TokenFalse, p.parseBooleanLiteral)
|
p.registerPrefix(lexer.TokenFalse, p.parseBooleanLiteral)
|
||||||
p.registerPrefix(lexer.TokenNot, p.parsePrefixExpression)
|
p.registerPrefix(lexer.TokenNot, p.parsePrefixExpression)
|
||||||
|
p.registerPrefix(lexer.TokenNil, p.parseNilLiteral)
|
||||||
|
|
||||||
// Initialize infix parse functions
|
// Initialize infix parse functions
|
||||||
p.infixParseFns = make(map[lexer.TokenType]infixParseFn)
|
p.infixParseFns = make(map[lexer.TokenType]infixParseFn)
|
||||||
@ -573,3 +574,7 @@ func (p *Parser) parseUnexpectedToken() Expression {
|
|||||||
p.curToken.Line, p.curToken.Value))
|
p.curToken.Line, p.curToken.Value))
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (p *Parser) parseNilLiteral() Expression {
|
||||||
|
return &NilLiteral{Token: p.curToken}
|
||||||
|
}
|
||||||
|
4
vm/vm.go
4
vm/vm.go
@ -190,7 +190,7 @@ func (vm *VM) Run(bytecode *types.Bytecode) {
|
|||||||
case types.TypeBoolean:
|
case types.TypeBoolean:
|
||||||
fmt.Println(value.Data.(bool))
|
fmt.Println(value.Data.(bool))
|
||||||
case types.TypeNull:
|
case types.TypeNull:
|
||||||
fmt.Println("null")
|
fmt.Println("nil")
|
||||||
case types.TypeTable:
|
case types.TypeTable:
|
||||||
fmt.Println(vm.formatTable(value.Data.(*types.Table)))
|
fmt.Println(vm.formatTable(value.Data.(*types.Table)))
|
||||||
}
|
}
|
||||||
@ -465,7 +465,7 @@ func (vm *VM) formatValue(value types.Value) string {
|
|||||||
case types.TypeBoolean:
|
case types.TypeBoolean:
|
||||||
return fmt.Sprintf("%v", value.Data.(bool))
|
return fmt.Sprintf("%v", value.Data.(bool))
|
||||||
case types.TypeNull:
|
case types.TypeNull:
|
||||||
return "null"
|
return "nil"
|
||||||
case types.TypeTable:
|
case types.TypeTable:
|
||||||
return vm.formatTable(value.Data.(*types.Table))
|
return vm.formatTable(value.Data.(*types.Table))
|
||||||
default:
|
default:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user