all: add optional args
This commit is contained in:
64
ast/ast.go
64
ast/ast.go
@@ -3,6 +3,8 @@ package ast
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
|
||||
"github.com/cevaris/ordered_map"
|
||||
)
|
||||
|
||||
type AST struct {
|
||||
@@ -21,8 +23,8 @@ const (
|
||||
Fn
|
||||
Char
|
||||
Table
|
||||
Prim
|
||||
Quoted
|
||||
Prim
|
||||
Quoted
|
||||
)
|
||||
|
||||
func (tag Tag) String() string {
|
||||
@@ -56,20 +58,20 @@ func (ast *AST) Type() *AST {
|
||||
"cons",
|
||||
}
|
||||
|
||||
if ast.Tag == Quoted {
|
||||
return ast.Val.(*AST).Type()
|
||||
}
|
||||
if ast.Tag == Quoted {
|
||||
return ast.Val.(*AST).Type()
|
||||
}
|
||||
|
||||
name := names[ast.Tag]
|
||||
if ast.Tag == Num {
|
||||
val := ast.Val.(float64)
|
||||
if val == float64(int64(val)) {
|
||||
name = "int"
|
||||
}
|
||||
}
|
||||
name := names[ast.Tag]
|
||||
if ast.Tag == Num {
|
||||
val := ast.Val.(float64)
|
||||
if val == float64(int64(val)) {
|
||||
name = "int"
|
||||
}
|
||||
}
|
||||
|
||||
res := AST{Symbol, name}
|
||||
return &res
|
||||
res := AST{Symbol, name}
|
||||
return &res
|
||||
}
|
||||
|
||||
func (ast *AST) Pretty() string {
|
||||
@@ -87,11 +89,12 @@ func (ast *AST) Pretty() string {
|
||||
for _, elem := range val.Params {
|
||||
agg = append(agg, elem)
|
||||
}
|
||||
opt := ""
|
||||
if val.HasOpt() {
|
||||
opt = " . " + *val.Opt
|
||||
}
|
||||
body := val.Body.Pretty()
|
||||
opt := ""
|
||||
if val.HasRest() {
|
||||
opt = " . " + *val.Rest
|
||||
}
|
||||
// TODO: opt
|
||||
body := val.Body.Pretty()
|
||||
return "(fn (" + strings.Join(agg, " ") + opt + ") " + body + ")"
|
||||
} else if ast.Tag == Char {
|
||||
return "#" + string(ast.Val.(rune))
|
||||
@@ -104,8 +107,8 @@ func (ast *AST) Pretty() string {
|
||||
|
||||
return "#hash(" + strings.Join(agg, " ") + ")"
|
||||
} else if ast.Tag == Prim {
|
||||
return "#<procedure: " + ast.Val.(Primitive).Name + ">"
|
||||
}
|
||||
return "#<procedure: " + ast.Val.(Primitive).Name + ">"
|
||||
}
|
||||
return fmt.Sprintf("%v", ast.Val)
|
||||
}
|
||||
|
||||
@@ -117,16 +120,16 @@ type Env struct {
|
||||
type PrimFn func([]*AST) (*AST, error)
|
||||
|
||||
type Primitive struct {
|
||||
Name string
|
||||
Fn PrimFn
|
||||
Name string
|
||||
Fn PrimFn
|
||||
}
|
||||
|
||||
func newEnv(parent *Env) Env {
|
||||
func NewEnv(parent *Env) Env {
|
||||
return Env{parent, make(map[string]*AST)}
|
||||
}
|
||||
|
||||
func ParentEnv() Env {
|
||||
return newEnv(nil)
|
||||
return NewEnv(nil)
|
||||
}
|
||||
|
||||
func (e *Env) Lookup(elem string) (*AST, error) {
|
||||
@@ -145,11 +148,16 @@ func (e *Env) Lookup(elem string) (*AST, error) {
|
||||
|
||||
type Func struct {
|
||||
Params []string
|
||||
Opt *string
|
||||
Rest *string
|
||||
Opt *ordered_map.OrderedMap
|
||||
Body *AST
|
||||
Env Env
|
||||
}
|
||||
|
||||
func (f *Func) HasOpt() bool {
|
||||
return f.Opt != nil
|
||||
func (f *Func) HasRest() bool {
|
||||
return f.Rest != nil
|
||||
}
|
||||
|
||||
func (f *Func) HasOpt() bool {
|
||||
return f.Opt.Len() != 0
|
||||
}
|
||||
|
Reference in New Issue
Block a user