From 37e6e24447936225a459a2ebc0fee84ba09dd0d0 Mon Sep 17 00:00:00 2001 From: Aidan Date: Fri, 14 Aug 2020 15:59:38 -0700 Subject: [PATCH] add split function --- stdlib/stdlib.go | 7 +++++++ stdlib/string.go | 42 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 49 insertions(+) diff --git a/stdlib/stdlib.go b/stdlib/stdlib.go index 9080b15..83f40fd 100644 --- a/stdlib/stdlib.go +++ b/stdlib/stdlib.go @@ -143,6 +143,13 @@ func GenFuncTable() ast.FuncTable { Args: -1, }, + "split": &ast.Function{ + Function: Split, + Name: "split", + TimesCalled: 0, + Args: 2, + }, + "exit": &ast.Function{ Function: ExitShell, Name: "exit", diff --git a/stdlib/string.go b/stdlib/string.go index 3cae616..e9f00be 100644 --- a/stdlib/string.go +++ b/stdlib/string.go @@ -19,6 +19,7 @@ package stdlib import ( "fmt" + "strings" "strconv" "gitlab.com/whom/shs/ast" "gitlab.com/whom/shs/log" @@ -59,6 +60,47 @@ func StrCast(in *ast.Token, vt ast.VarTable, ft ast.FuncTable) *ast.Token { return res } +/* Takes 2 arguments, a string and a delimiter + * returns a list of substrings found delimited by the delimiter from the parent string + * Filters out all empty segments between delimiters + * + * Example: (split "/path/to/file" "/") -> ("path" "to" "file") + */ +func Split(in *ast.Token, vt ast.VarTable, ft ast.FuncTable) *ast.Token { + in = in.Eval(ft, vt, false) + if in == nil || in.Tag != ast.STRING || in.Next == nil || in.Next.Tag != ast.STRING { + log.Log(log.ERR, + "Args must be two strings", + "split") + return nil + } + + body := in.Value() + delim := in.Next.Value() + if len(body) < len(delim) { + log.Log(log.DEBUG, + "possibly mismatched args" + + "delimiter longer than body", + "split") + } + + var res *ast.Token + builder := &res + strtoks := strings.Split(body, delim) + for _, i := range strtoks { + if i == "" { + continue + } + + *builder = &ast.Token{Tag: ast.STRING} + (*builder).Set(i) + builder = &(*builder).Next + } + + return res +} + + /* Takes one arg, returns nil * Prints a string to stdout * Unquotes string so user can add escaped chars like \n, \t, etc