eval: add maptable

This commit is contained in:
2018-05-14 22:17:12 +02:00
parent f114369c65
commit a3a84dcb98
2 changed files with 45 additions and 1 deletions

View File

@@ -7,7 +7,6 @@
## TODOS
- Destructuring assignment
- `maptable`
- `coerce`
- `mac`
- `````

View File

@@ -481,6 +481,49 @@ func evalLen(l []*ast.AST) (*ast.AST, error) {
return &res, nil
}
func evalMapTable(l []*ast.AST, e ast.Env) (*ast.AST, error) {
err := checkArity(l, 2, "maptable")
if err != nil {
return nil, err
}
f, err := Eval(l[0], e)
if err != nil {
return nil, err
}
maybeLst, err := Eval(l[1], e)
if err != nil {
return nil, err
}
if maybeLst.Tag != ast.Table {
return nil, fmt.Errorf("Second argument to maptable must be table")
}
lst := maybeLst.Val.(map[*ast.AST]*ast.AST)
var res []*ast.AST
for k, v := range lst {
toEval := ast.AST{ast.List, []*ast.AST{f, k, v}}
evald, err := Eval(&toEval, e)
if err != nil {
return nil, err
}
res = append(res, evald)
}
reslst := ast.AST{ast.List, res}
quoted := ast.AST{ast.Quoted, &reslst}
return &quoted, nil
}
func evalSymbolList(l []*ast.AST, e ast.Env) (*ast.AST, error) {
sym := l[0].Val.(string)
@@ -519,6 +562,8 @@ func evalSymbolList(l []*ast.AST, e ast.Env) (*ast.AST, error) {
return evalLog(l, e, func(x float64, y float64) bool { return x < y })
case ">":
return evalLog(l, e, func(x float64, y float64) bool { return x > y })
case "maptable":
return evalMapTable(l, e)
}
res, err := e.Lookup(sym)