builtins
Some checks failed
Build / build (push) Failing after 1h2m55s
Test / build (push) Failing after 29m38s

This commit is contained in:
Chuck Smith
2024-03-12 16:35:24 -04:00
parent 1d2c7f0a51
commit e373e9f68a
11 changed files with 354 additions and 125 deletions

139
object/builtins.go Normal file
View File

@@ -0,0 +1,139 @@
package object
import "fmt"
var Builtins = []struct {
Name string
Builtin *Builtin
}{
{
"len",
&Builtin{Fn: func(args ...Object) Object {
if len(args) != 1 {
return newError("wrong number of arguments. got=%d, want=1",
len(args))
}
switch arg := args[0].(type) {
case *Array:
return &Integer{Value: int64(len(arg.Elements))}
case *String:
return &Integer{Value: int64(len(arg.Value))}
default:
return newError("argument to `len` not supported, got %s",
args[0].Type())
}
},
},
},
{
"puts",
&Builtin{Fn: func(args ...Object) Object {
for _, arg := range args {
fmt.Println(arg.Inspect())
}
return nil
},
},
},
{
"first",
&Builtin{Fn: func(args ...Object) Object {
if len(args) != 1 {
return newError("wrong number of arguments. got=%d, want=1", len(args))
}
if args[0].Type() != ARRAY_OBJ {
return newError("argument to `first` must be ARRAY, got %s", args[0].Type())
}
arr := args[0].(*Array)
if len(arr.Elements) > 0 {
return arr.Elements[0]
}
return nil
},
},
},
{
"last",
&Builtin{Fn: func(args ...Object) Object {
if len(args) != 1 {
return newError("wrong number of arguments. got=%d, want=1", len(args))
}
if args[0].Type() != ARRAY_OBJ {
return newError("argument to `last` must be ARRAY, got %s", args[0].Type())
}
arr := args[0].(*Array)
length := len(arr.Elements)
if length > 0 {
return arr.Elements[length-1]
}
return nil
},
},
},
{
"rest",
&Builtin{Fn: func(args ...Object) Object {
if len(args) != 1 {
return newError("wrong number of arguments. got=%d, want=1",
len(args))
}
if args[0].Type() != ARRAY_OBJ {
return newError("argument to `rest` must be ARRAY, got %s",
args[0].Type())
}
arr := args[0].(*Array)
length := len(arr.Elements)
if length > 0 {
newElements := make([]Object, length-1, length-1)
copy(newElements, arr.Elements[1:length])
return &Array{Elements: newElements}
}
return nil
},
},
},
{
"push",
&Builtin{Fn: func(args ...Object) Object {
if len(args) != 2 {
return newError("wrong number of arguments. got=%d, want=2",
len(args))
}
if args[0].Type() != ARRAY_OBJ {
return newError("argument to `push` must be ARRAY, got %s",
args[0].Type())
}
arr := args[0].(*Array)
length := len(arr.Elements)
newElements := make([]Object, length+1, length+1)
copy(newElements, arr.Elements)
newElements[length] = args[1]
return &Array{Elements: newElements}
},
},
},
}
func newError(format string, a ...interface{}) *Error {
return &Error{Message: fmt.Sprintf(format, a...)}
}
func GetBuiltinByName(name string) *Builtin {
for _, def := range Builtins {
if def.Name == name {
return def.Builtin
}
}
return nil
}