made some interfaces exportable and fixed/enhaaced some selector operator versions
This commit is contained in:
parent
aa195b9a68
commit
9ac88bf446
18
ast.go
18
ast.go
@ -10,7 +10,8 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type Expr interface {
|
type Expr interface {
|
||||||
Eval(ctx exprContext, preset bool) (result any, err error)
|
Eval(ctx ExprContext) (result any, err error)
|
||||||
|
eval(ctx ExprContext, preset bool) (result any, err error)
|
||||||
}
|
}
|
||||||
|
|
||||||
//-------- ast
|
//-------- ast
|
||||||
@ -58,15 +59,6 @@ func (self *ast) addToken(tk *Token) (err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// func (self *ast) addToken(tk *Token) (err error) {
|
|
||||||
// if t := newTerm(tk, nil); t != nil {
|
|
||||||
// err = self.addTerm(t)
|
|
||||||
// } else {
|
|
||||||
// err = tk.Errorf("No term constructor for token %q", tk.String())
|
|
||||||
// }
|
|
||||||
// return
|
|
||||||
// }
|
|
||||||
|
|
||||||
func (self *ast) addToken2(tk *Token) (t *term, err error) {
|
func (self *ast) addToken2(tk *Token) (t *term, err error) {
|
||||||
if t = newTerm(tk, nil); t != nil {
|
if t = newTerm(tk, nil); t != nil {
|
||||||
err = self.addTerm(t)
|
err = self.addTerm(t)
|
||||||
@ -112,7 +104,11 @@ func (self *ast) Finish() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (self *ast) Eval(ctx exprContext, preset bool) (result any, err error) {
|
func (self *ast) Eval(ctx ExprContext) (result any, err error) {
|
||||||
|
return self.eval(ctx, true)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (self *ast) eval(ctx ExprContext, preset bool) (result any, err error) {
|
||||||
self.Finish()
|
self.Finish()
|
||||||
|
|
||||||
if self.root != nil {
|
if self.root != nil {
|
||||||
|
14
context.go
14
context.go
@ -5,23 +5,23 @@
|
|||||||
package expr
|
package expr
|
||||||
|
|
||||||
// ---- Function template
|
// ---- Function template
|
||||||
type FuncTemplate func(ctx exprContext, name string, args []any) (result any, err error)
|
type FuncTemplate func(ctx ExprContext, name string, args []any) (result any, err error)
|
||||||
|
|
||||||
// ---- Functor interface
|
// ---- Functor interface
|
||||||
type Functor interface {
|
type Functor interface {
|
||||||
Invoke(ctx exprContext, name string, args []any) (result any, err error)
|
Invoke(ctx ExprContext, name string, args []any) (result any, err error)
|
||||||
}
|
}
|
||||||
|
|
||||||
type simpleFunctor struct {
|
type simpleFunctor struct {
|
||||||
f FuncTemplate
|
f FuncTemplate
|
||||||
}
|
}
|
||||||
|
|
||||||
func (functor *simpleFunctor) Invoke(ctx exprContext, name string, args []any) (result any, err error) {
|
func (functor *simpleFunctor) Invoke(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
return functor.f(ctx, name, args)
|
return functor.f(ctx, name, args)
|
||||||
}
|
}
|
||||||
|
|
||||||
// ---- Function Info
|
// ---- Function Info
|
||||||
type exprFunc interface {
|
type ExprFunc interface {
|
||||||
Name() string
|
Name() string
|
||||||
MinArgs() int
|
MinArgs() int
|
||||||
MaxArgs() int
|
MaxArgs() int
|
||||||
@ -29,13 +29,13 @@ type exprFunc interface {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ----Expression Context
|
// ----Expression Context
|
||||||
type exprContext interface {
|
type ExprContext interface {
|
||||||
Clone() exprContext
|
Clone() ExprContext
|
||||||
GetVar(varName string) (value any, exists bool)
|
GetVar(varName string) (value any, exists bool)
|
||||||
SetVar(varName string, value any)
|
SetVar(varName string, value any)
|
||||||
EnumVars(func(name string) (accept bool)) (varNames []string)
|
EnumVars(func(name string) (accept bool)) (varNames []string)
|
||||||
EnumFuncs(func(name string) (accept bool)) (funcNames []string)
|
EnumFuncs(func(name string) (accept bool)) (funcNames []string)
|
||||||
GetFuncInfo(name string) exprFunc
|
GetFuncInfo(name string) ExprFunc
|
||||||
Call(name string, args []any) (result any, err error)
|
Call(name string, args []any) (result any, err error)
|
||||||
RegisterFunc(name string, f Functor, minArgs, maxArgs int)
|
RegisterFunc(name string, f Functor, minArgs, maxArgs int)
|
||||||
}
|
}
|
||||||
|
10
control.go
10
control.go
@ -20,12 +20,12 @@ const (
|
|||||||
init_import_path = "~/.local/lib/go-pkg/expr:/usr/local/lib/go-pkg/expr:/usr/lib/go-pkg/expr"
|
init_import_path = "~/.local/lib/go-pkg/expr:/usr/local/lib/go-pkg/expr:/usr/lib/go-pkg/expr"
|
||||||
)
|
)
|
||||||
|
|
||||||
func initDefaultVars(ctx exprContext) {
|
func initDefaultVars(ctx ExprContext) {
|
||||||
ctx.SetVar(control_bool_shortcut, true)
|
ctx.SetVar(control_bool_shortcut, true)
|
||||||
ctx.SetVar(control_import_path, init_import_path)
|
ctx.SetVar(control_import_path, init_import_path)
|
||||||
}
|
}
|
||||||
|
|
||||||
func enable(ctx exprContext, name string) {
|
func enable(ctx ExprContext, name string) {
|
||||||
if strings.HasPrefix(name, "_") {
|
if strings.HasPrefix(name, "_") {
|
||||||
ctx.SetVar(name, true)
|
ctx.SetVar(name, true)
|
||||||
} else {
|
} else {
|
||||||
@ -33,7 +33,7 @@ func enable(ctx exprContext, name string) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func disable(ctx exprContext, name string) {
|
func disable(ctx ExprContext, name string) {
|
||||||
if strings.HasPrefix(name, "_") {
|
if strings.HasPrefix(name, "_") {
|
||||||
ctx.SetVar(name, false)
|
ctx.SetVar(name, false)
|
||||||
} else {
|
} else {
|
||||||
@ -41,7 +41,7 @@ func disable(ctx exprContext, name string) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func isEnabled(ctx exprContext, name string) (status bool) {
|
func isEnabled(ctx ExprContext, name string) (status bool) {
|
||||||
if v, exists := ctx.GetVar(name); exists {
|
if v, exists := ctx.GetVar(name); exists {
|
||||||
if b, ok := v.(bool); ok {
|
if b, ok := v.(bool); ok {
|
||||||
status = b
|
status = b
|
||||||
@ -50,7 +50,7 @@ func isEnabled(ctx exprContext, name string) (status bool) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func getControlString(ctx exprContext, name string) (s string, exists bool) {
|
func getControlString(ctx ExprContext, name string) (s string, exists bool) {
|
||||||
var v any
|
var v any
|
||||||
if v, exists = ctx.GetVar(name); exists {
|
if v, exists = ctx.GetVar(name); exists {
|
||||||
s, exists = v.(string)
|
s, exists = v.(string)
|
||||||
|
@ -13,16 +13,16 @@ import (
|
|||||||
|
|
||||||
const ENV_EXPR_PATH = "EXPR_PATH"
|
const ENV_EXPR_PATH = "EXPR_PATH"
|
||||||
|
|
||||||
func importFunc(ctx exprContext, name string, args []any) (result any, err error) {
|
func importFunc(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
return importGeneral(ctx, name, args)
|
return importGeneral(ctx, name, args)
|
||||||
}
|
}
|
||||||
|
|
||||||
func includeFunc(ctx exprContext, name string, args []any) (result any, err error) {
|
func includeFunc(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
enable(ctx, control_export_all)
|
enable(ctx, control_export_all)
|
||||||
return importGeneral(ctx, name, args)
|
return importGeneral(ctx, name, args)
|
||||||
}
|
}
|
||||||
|
|
||||||
func importGeneral(ctx exprContext, name string, args []any) (result any, err error) {
|
func importGeneral(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
var dirList []string
|
var dirList []string
|
||||||
|
|
||||||
dirList = addEnvImportDirs(dirList)
|
dirList = addEnvImportDirs(dirList)
|
||||||
@ -50,7 +50,7 @@ func addEnvImportDirs(dirList []string) []string {
|
|||||||
return dirList
|
return dirList
|
||||||
}
|
}
|
||||||
|
|
||||||
func addPresetImportDirs(ctx exprContext, dirList []string) []string {
|
func addPresetImportDirs(ctx ExprContext, dirList []string) []string {
|
||||||
if dirSpec, exists := getControlString(ctx, control_import_path); exists {
|
if dirSpec, exists := getControlString(ctx, control_import_path); exists {
|
||||||
dirs := strings.Split(dirSpec, ":")
|
dirs := strings.Split(dirSpec, ":")
|
||||||
if dirList == nil {
|
if dirList == nil {
|
||||||
@ -96,7 +96,7 @@ func makeFilepath(filename string, dirList []string) (filePath string, err error
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func doImport(ctx exprContext, name string, dirList []string, it Iterator) (result any, err error) {
|
func doImport(ctx ExprContext, name string, dirList []string, it Iterator) (result any, err error) {
|
||||||
var v any
|
var v any
|
||||||
var sourceFilepath string
|
var sourceFilepath string
|
||||||
|
|
||||||
@ -114,7 +114,7 @@ func doImport(ctx exprContext, name string, dirList []string, it Iterator) (resu
|
|||||||
scanner := NewScanner(file, DefaultTranslations())
|
scanner := NewScanner(file, DefaultTranslations())
|
||||||
parser := NewParser(ctx)
|
parser := NewParser(ctx)
|
||||||
if expr, err = parser.parseGeneral(scanner, true, true); err == nil {
|
if expr, err = parser.parseGeneral(scanner, true, true); err == nil {
|
||||||
result, err = expr.Eval(ctx, false)
|
result, err = expr.eval(ctx, false)
|
||||||
}
|
}
|
||||||
if err != nil {
|
if err != nil {
|
||||||
break
|
break
|
||||||
@ -133,7 +133,7 @@ func doImport(ctx exprContext, name string, dirList []string, it Iterator) (resu
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func importImportFunc(ctx exprContext) {
|
func importImportFunc(ctx ExprContext) {
|
||||||
ctx.RegisterFunc("import", &simpleFunctor{f: importFunc}, 1, -1)
|
ctx.RegisterFunc("import", &simpleFunctor{f: importFunc}, 1, -1)
|
||||||
ctx.RegisterFunc("include", &simpleFunctor{f: includeFunc}, 1, -1)
|
ctx.RegisterFunc("include", &simpleFunctor{f: includeFunc}, 1, -1)
|
||||||
}
|
}
|
||||||
|
10
func-math.go
10
func-math.go
@ -13,7 +13,7 @@ func checkNumberParamExpected(funcName string, paramValue any, paramPos int) (er
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func doAdd(ctx exprContext, name string, it Iterator) (result any, err error) {
|
func doAdd(ctx ExprContext, name string, it Iterator) (result any, err error) {
|
||||||
var sumAsFloat = false
|
var sumAsFloat = false
|
||||||
var floatSum float64 = 0.0
|
var floatSum float64 = 0.0
|
||||||
var intSum int64 = 0
|
var intSum int64 = 0
|
||||||
@ -52,12 +52,12 @@ func doAdd(ctx exprContext, name string, it Iterator) (result any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func addFunc(ctx exprContext, name string, args []any) (result any, err error) {
|
func addFunc(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
result, err = doAdd(ctx, name, NewFlatArrayIterator(args))
|
result, err = doAdd(ctx, name, NewFlatArrayIterator(args))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func doMul(ctx exprContext, name string, it Iterator) (result any, err error) {
|
func doMul(ctx ExprContext, name string, it Iterator) (result any, err error) {
|
||||||
var mulAsFloat = false
|
var mulAsFloat = false
|
||||||
var floatProd float64 = 1.0
|
var floatProd float64 = 1.0
|
||||||
var intProd int64 = 1
|
var intProd int64 = 1
|
||||||
@ -96,12 +96,12 @@ func doMul(ctx exprContext, name string, it Iterator) (result any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func mulFunc(ctx exprContext, name string, args []any) (result any, err error) {
|
func mulFunc(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
result, err = doMul(ctx, name, NewFlatArrayIterator(args))
|
result, err = doMul(ctx, name, NewFlatArrayIterator(args))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func importMathFuncs(ctx exprContext) {
|
func importMathFuncs(ctx ExprContext) {
|
||||||
ctx.RegisterFunc("add", &simpleFunctor{f: addFunc}, 0, -1)
|
ctx.RegisterFunc("add", &simpleFunctor{f: addFunc}, 0, -1)
|
||||||
ctx.RegisterFunc("mul", &simpleFunctor{f: mulFunc}, 0, -1)
|
ctx.RegisterFunc("mul", &simpleFunctor{f: mulFunc}, 0, -1)
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
func EvalString(ctx exprContext, source string) (result any, err error) {
|
func EvalString(ctx ExprContext, source string) (result any, err error) {
|
||||||
var tree *ast
|
var tree *ast
|
||||||
|
|
||||||
r := strings.NewReader(source)
|
r := strings.NewReader(source)
|
||||||
@ -14,7 +14,7 @@ func EvalString(ctx exprContext, source string) (result any, err error) {
|
|||||||
parser := NewParser(ctx)
|
parser := NewParser(ctx)
|
||||||
|
|
||||||
if tree, err = parser.Parse(scanner); err == nil {
|
if tree, err = parser.Parse(scanner); err == nil {
|
||||||
result, err = tree.Eval(ctx, true)
|
result, err = tree.eval(ctx, true)
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,7 @@ import (
|
|||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
||||||
func subtract(ctx exprContext, name string, args []any) (result any, err error) {
|
func subtract(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
if len(args) != 2 {
|
if len(args) != 2 {
|
||||||
err = fmt.Errorf("%s(): requires exactly two arguments", name)
|
err = fmt.Errorf("%s(): requires exactly two arguments", name)
|
||||||
return
|
return
|
||||||
|
@ -61,7 +61,7 @@ func newStringTerm(tk *Token) *term {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -------- eval func
|
// -------- eval func
|
||||||
func evalConst(ctx exprContext, self *term) (v any, err error) {
|
func evalConst(ctx ExprContext, self *term) (v any, err error) {
|
||||||
v = self.tk.Value
|
v = self.tk.Value
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -21,9 +21,9 @@ func newExprTerm(tk *Token) *term {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -------- eval expr
|
// -------- eval expr
|
||||||
func evalExpr(ctx exprContext, self *term) (v any, err error) {
|
func evalExpr(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if expr, ok := self.value().(Expr); ok {
|
if expr, ok := self.value().(Expr); ok {
|
||||||
v, err = expr.Eval(ctx, false)
|
v, err = expr.eval(ctx, false)
|
||||||
} else {
|
} else {
|
||||||
err = fmt.Errorf("expression expected, got %T", self.value())
|
err = fmt.Errorf("expression expected, got %T", self.value())
|
||||||
}
|
}
|
||||||
|
@ -23,7 +23,7 @@ func newFuncCallTerm(tk *Token, args []*term) *term {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -------- eval func call
|
// -------- eval func call
|
||||||
func evalFuncCall(parentCtx exprContext, self *term) (v any, err error) {
|
func evalFuncCall(parentCtx ExprContext, self *term) (v any, err error) {
|
||||||
ctx := parentCtx.Clone()
|
ctx := parentCtx.Clone()
|
||||||
name, _ := self.tk.Value.(string)
|
name, _ := self.tk.Value.(string)
|
||||||
params := make([]any, len(self.children))
|
params := make([]any, len(self.children))
|
||||||
@ -53,14 +53,14 @@ func evalFuncCall(parentCtx exprContext, self *term) (v any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func exportVar(ctx exprContext, name string, value any) {
|
func exportVar(ctx ExprContext, name string, value any) {
|
||||||
if name[0] == '@' {
|
if name[0] == '@' {
|
||||||
name = name[1:]
|
name = name[1:]
|
||||||
}
|
}
|
||||||
ctx.SetVar(name, value)
|
ctx.SetVar(name, value)
|
||||||
}
|
}
|
||||||
|
|
||||||
func exportFunc(ctx exprContext, name string, info exprFunc) {
|
func exportFunc(ctx ExprContext, name string, info ExprFunc) {
|
||||||
if name[0] == '@' {
|
if name[0] == '@' {
|
||||||
name = name[1:]
|
name = name[1:]
|
||||||
}
|
}
|
||||||
@ -88,7 +88,7 @@ type funcDefFunctor struct {
|
|||||||
expr Expr
|
expr Expr
|
||||||
}
|
}
|
||||||
|
|
||||||
func (functor *funcDefFunctor) Invoke(ctx exprContext, name string, args []any) (result any, err error) {
|
func (functor *funcDefFunctor) Invoke(ctx ExprContext, name string, args []any) (result any, err error) {
|
||||||
for i, p := range functor.params {
|
for i, p := range functor.params {
|
||||||
if i < len(args) {
|
if i < len(args) {
|
||||||
ctx.SetVar(p, args[i])
|
ctx.SetVar(p, args[i])
|
||||||
@ -96,11 +96,11 @@ func (functor *funcDefFunctor) Invoke(ctx exprContext, name string, args []any)
|
|||||||
ctx.SetVar(p, nil)
|
ctx.SetVar(p, nil)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
result, err = functor.expr.Eval(ctx, false)
|
result, err = functor.expr.eval(ctx, false)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalFuncDef(ctx exprContext, self *term) (v any, err error) {
|
func evalFuncDef(ctx ExprContext, self *term) (v any, err error) {
|
||||||
bodySpec := self.value()
|
bodySpec := self.value()
|
||||||
if expr, ok := bodySpec.(*ast); ok {
|
if expr, ok := bodySpec.(*ast); ok {
|
||||||
paramList := make([]string, 0, len(self.children))
|
paramList := make([]string, 0, len(self.children))
|
||||||
|
@ -19,7 +19,7 @@ func newListTerm(args []*term) *term {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -------- list func
|
// -------- list func
|
||||||
func evalList(ctx exprContext, self *term) (v any, err error) {
|
func evalList(ctx ExprContext, self *term) (v any, err error) {
|
||||||
items := make([]any, len(self.children))
|
items := make([]any, len(self.children))
|
||||||
for i, tree := range self.children {
|
for i, tree := range self.children {
|
||||||
var param any
|
var param any
|
||||||
|
@ -28,7 +28,7 @@ func newSelectorCaseTerm(row, col int, filterList *term, caseExpr Expr) *term {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -------- eval selector case
|
// -------- eval selector case
|
||||||
func evalSelectorCase(ctx exprContext, self *term) (v any, err error) {
|
func evalSelectorCase(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var ok bool
|
var ok bool
|
||||||
if v, ok = self.value().(*selectorCase); !ok {
|
if v, ok = self.value().(*selectorCase); !ok {
|
||||||
err = fmt.Errorf("selector-case expected, got %T", self.value())
|
err = fmt.Errorf("selector-case expected, got %T", self.value())
|
||||||
|
@ -21,7 +21,7 @@ func newVarTerm(tk *Token) *term {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -------- eval func
|
// -------- eval func
|
||||||
func evalVar(ctx exprContext, self *term) (v any, err error) {
|
func evalVar(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var exists bool
|
var exists bool
|
||||||
if v, exists = ctx.GetVar(self.tk.source); !exists {
|
if v, exists = ctx.GetVar(self.tk.source); !exists {
|
||||||
err = fmt.Errorf("undefined variable %q", self.tk.source)
|
err = fmt.Errorf("undefined variable %q", self.tk.source)
|
||||||
|
@ -18,7 +18,7 @@ func newAssignTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalAssign(ctx exprContext, self *term) (v any, err error) {
|
func evalAssign(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if err = self.checkOperands(); err != nil {
|
if err = self.checkOperands(); err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -20,7 +20,7 @@ func newNotTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalNot(ctx exprContext, self *term) (v any, err error) {
|
func evalNot(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var rightValue any
|
var rightValue any
|
||||||
|
|
||||||
if rightValue, err = self.evalPrefix(ctx); err != nil {
|
if rightValue, err = self.evalPrefix(ctx); err != nil {
|
||||||
@ -49,7 +49,7 @@ func newAndTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalAnd(ctx exprContext, self *term) (v any, err error) {
|
func evalAnd(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if isEnabled(ctx, control_bool_shortcut) {
|
if isEnabled(ctx, control_bool_shortcut) {
|
||||||
v, err = evalAndWithShortcut(ctx, self)
|
v, err = evalAndWithShortcut(ctx, self)
|
||||||
} else {
|
} else {
|
||||||
@ -58,7 +58,7 @@ func evalAnd(ctx exprContext, self *term) (v any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalAndWithoutShortcut(ctx exprContext, self *term) (v any, err error) {
|
func evalAndWithoutShortcut(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
var leftBool, rightBool bool
|
var leftBool, rightBool bool
|
||||||
var lok, rok bool
|
var lok, rok bool
|
||||||
@ -78,7 +78,7 @@ func evalAndWithoutShortcut(ctx exprContext, self *term) (v any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalAndWithShortcut(ctx exprContext, self *term) (v any, err error) {
|
func evalAndWithShortcut(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if err = self.checkOperands(); err != nil {
|
if err = self.checkOperands(); err != nil {
|
||||||
@ -118,7 +118,7 @@ func newOrTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalOr(ctx exprContext, self *term) (v any, err error) {
|
func evalOr(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if isEnabled(ctx, control_bool_shortcut) {
|
if isEnabled(ctx, control_bool_shortcut) {
|
||||||
v, err = evalOrWithShortcut(ctx, self)
|
v, err = evalOrWithShortcut(ctx, self)
|
||||||
} else {
|
} else {
|
||||||
@ -127,7 +127,7 @@ func evalOr(ctx exprContext, self *term) (v any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalOrWithoutShortcut(ctx exprContext, self *term) (v any, err error) {
|
func evalOrWithoutShortcut(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
var leftBool, rightBool bool
|
var leftBool, rightBool bool
|
||||||
var lok, rok bool
|
var lok, rok bool
|
||||||
@ -147,7 +147,7 @@ func evalOrWithoutShortcut(ctx exprContext, self *term) (v any, err error) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalOrWithShortcut(ctx exprContext, self *term) (v any, err error) {
|
func evalOrWithShortcut(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if err = self.checkOperands(); err != nil {
|
if err = self.checkOperands(); err != nil {
|
||||||
|
@ -18,7 +18,7 @@ func newButTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalBut(ctx exprContext, self *term) (v any, err error) {
|
func evalBut(ctx ExprContext, self *term) (v any, err error) {
|
||||||
_, v, err = self.evalInfix(ctx)
|
_, v, err = self.evalInfix(ctx)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -18,7 +18,7 @@ func newNullCoalesceTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalNullCoalesce(ctx exprContext, self *term) (v any, err error) {
|
func evalNullCoalesce(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var rightValue any
|
var rightValue any
|
||||||
|
|
||||||
if err = self.checkOperands(); err != nil {
|
if err = self.checkOperands(); err != nil {
|
||||||
@ -57,7 +57,7 @@ func newCoalesceAssignTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalAssignCoalesce(ctx exprContext, self *term) (v any, err error) {
|
func evalAssignCoalesce(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var rightValue any
|
var rightValue any
|
||||||
|
|
||||||
if err = self.checkOperands(); err != nil {
|
if err = self.checkOperands(); err != nil {
|
||||||
|
@ -18,7 +18,7 @@ func newExportAllTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalExportAll(ctx exprContext, self *term) (v any, err error) {
|
func evalExportAll(ctx ExprContext, self *term) (v any, err error) {
|
||||||
enable(ctx, control_export_all)
|
enable(ctx, control_export_all)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -20,7 +20,7 @@ func newFactTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalFact(ctx exprContext, self *term) (v any, err error) {
|
func evalFact(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue any
|
var leftValue any
|
||||||
|
|
||||||
if leftValue, err = self.evalPrefix(ctx); err != nil {
|
if leftValue, err = self.evalPrefix(ctx); err != nil {
|
||||||
|
@ -23,7 +23,7 @@ func newMultiplyTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalMultiply(ctx exprContext, self *term) (v any, err error) {
|
func evalMultiply(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -62,7 +62,7 @@ func newDivideTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalDivide(ctx exprContext, self *term) (v any, err error) {
|
func evalDivide(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -105,7 +105,7 @@ func newDivideAsFloatTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalDivideAsFloat(ctx exprContext, self *term) (v any, err error) {
|
func evalDivideAsFloat(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -139,7 +139,7 @@ func newReminderTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalReminder(ctx exprContext, self *term) (v any, err error) {
|
func evalReminder(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
|
@ -18,7 +18,7 @@ func newEqualTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalEqual(ctx exprContext, self *term) (v any, err error) {
|
func evalEqual(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -57,7 +57,7 @@ func newNotEqualTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalNotEqual(ctx exprContext, self *term) (v any, err error) {
|
func evalNotEqual(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if v, err = evalEqual(ctx, self); err == nil {
|
if v, err = evalEqual(ctx, self); err == nil {
|
||||||
b, _ := toBool(v)
|
b, _ := toBool(v)
|
||||||
v = !b
|
v = !b
|
||||||
@ -104,7 +104,7 @@ func newLessTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalLess(ctx exprContext, self *term) (v any, err error) {
|
func evalLess(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -143,7 +143,7 @@ func newLessEqualTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalLessEqual(ctx exprContext, self *term) (v any, err error) {
|
func evalLessEqual(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -182,7 +182,7 @@ func newGreaterTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalGreater(ctx exprContext, self *term) (v any, err error) {
|
func evalGreater(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if v, err = evalLessEqual(ctx, self); err == nil {
|
if v, err = evalLessEqual(ctx, self); err == nil {
|
||||||
b, _ := toBool(v)
|
b, _ := toBool(v)
|
||||||
v = !b
|
v = !b
|
||||||
@ -204,7 +204,7 @@ func newGreaterEqualTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalGreaterEqual(ctx exprContext, self *term) (v any, err error) {
|
func evalGreaterEqual(ctx ExprContext, self *term) (v any, err error) {
|
||||||
if v, err = evalLess(ctx, self); err == nil {
|
if v, err = evalLess(ctx, self); err == nil {
|
||||||
b, _ := toBool(v)
|
b, _ := toBool(v)
|
||||||
v = !b
|
v = !b
|
||||||
|
@ -18,19 +18,19 @@ func newSelectorTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func isSelectorCase(ctx exprContext, exprValue, caseSel any, caseIndex int) (selectedValue any, err error) {
|
func isSelectorCase(ctx ExprContext, exprValue, caseSel any, caseIndex int) (selectedValue any, err error) {
|
||||||
caseData, _ := caseSel.(*selectorCase)
|
caseData, _ := caseSel.(*selectorCase)
|
||||||
if caseData.filterList == nil {
|
if caseData.filterList == nil {
|
||||||
selectedValue, err = caseData.caseExpr.Eval(ctx, false)
|
selectedValue, err = caseData.caseExpr.eval(ctx, false)
|
||||||
} else {
|
} else {
|
||||||
filterList := caseData.filterList.children
|
filterList := caseData.filterList.children
|
||||||
if len(filterList) == 0 && exprValue == int64(caseIndex) {
|
if len(filterList) == 0 && exprValue == int64(caseIndex) {
|
||||||
selectedValue, err = caseData.caseExpr.Eval(ctx, false)
|
selectedValue, err = caseData.caseExpr.eval(ctx, false)
|
||||||
} else {
|
} else {
|
||||||
var caseValue any
|
var caseValue any
|
||||||
for _, caseTerm := range filterList {
|
for _, caseTerm := range filterList {
|
||||||
if caseValue, err = caseTerm.compute(ctx); err != nil || caseValue == exprValue {
|
if caseValue, err = caseTerm.compute(ctx); err != nil || caseValue == exprValue {
|
||||||
selectedValue, err = caseData.caseExpr.Eval(ctx, false)
|
selectedValue, err = caseData.caseExpr.eval(ctx, false)
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -39,7 +39,7 @@ func isSelectorCase(ctx exprContext, exprValue, caseSel any, caseIndex int) (sel
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalSelector(ctx exprContext, self *term) (v any, err error) {
|
func evalSelector(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var exprValue any
|
var exprValue any
|
||||||
// var caseList []*term
|
// var caseList []*term
|
||||||
|
|
||||||
|
@ -30,7 +30,7 @@ func newMinusSignTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalSign(ctx exprContext, self *term) (v any, err error) {
|
func evalSign(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var rightValue any
|
var rightValue any
|
||||||
|
|
||||||
if rightValue, err = self.evalPrefix(ctx); err != nil {
|
if rightValue, err = self.evalPrefix(ctx); err != nil {
|
||||||
|
@ -23,7 +23,7 @@ func newPlusTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalPlus(ctx exprContext, self *term) (v any, err error) {
|
func evalPlus(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
@ -77,7 +77,7 @@ func newMinusTerm(tk *Token) (inst *term) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func evalMinus(ctx exprContext, self *term) (v any, err error) {
|
func evalMinus(ctx ExprContext, self *term) (v any, err error) {
|
||||||
var leftValue, rightValue any
|
var leftValue, rightValue any
|
||||||
|
|
||||||
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
if leftValue, rightValue, err = self.evalInfix(ctx); err != nil {
|
||||||
|
11
parser.go
11
parser.go
@ -12,10 +12,10 @@ import (
|
|||||||
//-------- parser
|
//-------- parser
|
||||||
|
|
||||||
type parser struct {
|
type parser struct {
|
||||||
ctx exprContext
|
ctx ExprContext
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewParser(ctx exprContext) (p *parser) {
|
func NewParser(ctx ExprContext) (p *parser) {
|
||||||
p = &parser{
|
p = &parser{
|
||||||
ctx: ctx,
|
ctx: ctx,
|
||||||
}
|
}
|
||||||
@ -246,9 +246,9 @@ func (self *parser) parseGeneral(scanner *scanner, allowForest bool, allowVarRef
|
|||||||
currentTerm, err = tree.addToken2(tk)
|
currentTerm, err = tree.addToken2(tk)
|
||||||
}
|
}
|
||||||
case SymQuestion:
|
case SymQuestion:
|
||||||
if selectorTerm != nil {
|
/*if selectorTerm != nil {
|
||||||
err = tk.Errorf("nested selectors must be enclosed in parentheses")
|
err = tk.Errorf("nested selectors must be enclosed in parentheses")
|
||||||
} else if selectorTerm, err = self.parseSelector(scanner, tree, allowVarRef); err == nil {
|
} else*/if selectorTerm, err = self.parseSelector(scanner, tree, allowVarRef); err == nil {
|
||||||
currentTerm = selectorTerm
|
currentTerm = selectorTerm
|
||||||
}
|
}
|
||||||
case SymColon, SymDoubleColon:
|
case SymColon, SymDoubleColon:
|
||||||
@ -259,6 +259,9 @@ func (self *parser) parseGeneral(scanner *scanner, allowForest bool, allowVarRef
|
|||||||
selectorTerm.children = append(selectorTerm.children, caseTerm)
|
selectorTerm.children = append(selectorTerm.children, caseTerm)
|
||||||
caseTerm.parent = selectorTerm
|
caseTerm.parent = selectorTerm
|
||||||
currentTerm = caseTerm
|
currentTerm = caseTerm
|
||||||
|
if tk.Sym == SymDoubleColon {
|
||||||
|
selectorTerm = nil
|
||||||
|
}
|
||||||
}
|
}
|
||||||
//resetSelector = tk.Sym == SymDoubleColon
|
//resetSelector = tk.Sym == SymDoubleColon
|
||||||
default:
|
default:
|
||||||
|
@ -153,6 +153,8 @@ func TestParser(t *testing.T) {
|
|||||||
/* 132 */ {`10 ? {"a"} :[10] {x="b" but x} :: {"c"}`, "b", nil},
|
/* 132 */ {`10 ? {"a"} :[10] {x="b" but x} :: {"c"}`, "b", nil},
|
||||||
/* 133 */ {`10 ? {"a"} :[10] {x="b"; x} :: {"c"}`, "b", nil},
|
/* 133 */ {`10 ? {"a"} :[10] {x="b"; x} :: {"c"}`, "b", nil},
|
||||||
/* 134 */ {`10 ? {"a"} : {"b"}`, nil, errors.New(`[1:3] no case catches the value (10) of the selection expression`)},
|
/* 134 */ {`10 ? {"a"} : {"b"}`, nil, errors.New(`[1:3] no case catches the value (10) of the selection expression`)},
|
||||||
|
/* 135 */ {`10 ? {"a"} :: {"b"} : {"c"}`, nil, errors.New(`[1:22] selector-case outside of a selector context`)},
|
||||||
|
/* 136 */ {`1 ? {"a"} : {"b"} ? ["a"] {"A"} :["b"] {"B"}`, "B", nil},
|
||||||
}
|
}
|
||||||
check_env_expr_path := 113
|
check_env_expr_path := 113
|
||||||
|
|
||||||
@ -160,11 +162,11 @@ func TestParser(t *testing.T) {
|
|||||||
failed := 0
|
failed := 0
|
||||||
|
|
||||||
// inputs1 := []inputType{
|
// inputs1 := []inputType{
|
||||||
// {`1 ? {"a"} : {"b"}`, "b", nil},
|
// {`1 ? {"a"} : {"b"} ? ["a"] {"A"} :["b"] {"B"}`, "B", nil},
|
||||||
// }
|
// }
|
||||||
|
|
||||||
for i, input := range inputs {
|
for i, input := range inputs {
|
||||||
var expr *ast
|
var expr Expr
|
||||||
var gotResult any
|
var gotResult any
|
||||||
var gotErr error
|
var gotErr error
|
||||||
|
|
||||||
@ -182,7 +184,7 @@ func TestParser(t *testing.T) {
|
|||||||
|
|
||||||
good := true
|
good := true
|
||||||
if expr, gotErr = parser.Parse(scanner); gotErr == nil {
|
if expr, gotErr = parser.Parse(scanner); gotErr == nil {
|
||||||
gotResult, gotErr = expr.Eval(ctx, true)
|
gotResult, gotErr = expr.Eval(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
if gotResult != input.wantResult {
|
if gotResult != input.wantResult {
|
||||||
@ -209,7 +211,7 @@ func TestParser(t *testing.T) {
|
|||||||
t.Log(fmt.Sprintf("test count: %d, succeeded count: %d, failed count: %d", len(inputs), succeeded, failed))
|
t.Log(fmt.Sprintf("test count: %d, succeeded count: %d, failed count: %d", len(inputs), succeeded, failed))
|
||||||
}
|
}
|
||||||
|
|
||||||
func NoTestListParser(t *testing.T) {
|
func TestListParser(t *testing.T) {
|
||||||
type inputType struct {
|
type inputType struct {
|
||||||
source string
|
source string
|
||||||
wantResult any
|
wantResult any
|
||||||
@ -257,7 +259,7 @@ func NoTestListParser(t *testing.T) {
|
|||||||
|
|
||||||
good := true
|
good := true
|
||||||
if expr, gotErr = parser.Parse(scanner); gotErr == nil {
|
if expr, gotErr = parser.Parse(scanner); gotErr == nil {
|
||||||
gotResult, gotErr = expr.Eval(ctx, true)
|
gotResult, gotErr = expr.Eval(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (gotResult == nil && input.wantResult != nil) || (gotResult != nil && input.wantResult == nil) {
|
if (gotResult == nil && input.wantResult != nil) || (gotResult != nil && input.wantResult == nil) {
|
||||||
|
@ -38,14 +38,14 @@ func NewSimpleFuncStore() *SimpleFuncStore {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctx *SimpleFuncStore) Clone() exprContext {
|
func (ctx *SimpleFuncStore) Clone() ExprContext {
|
||||||
return &SimpleFuncStore{
|
return &SimpleFuncStore{
|
||||||
SimpleVarStore: SimpleVarStore{varStore: CloneMap(ctx.varStore)},
|
SimpleVarStore: SimpleVarStore{varStore: CloneMap(ctx.varStore)},
|
||||||
funcStore: CloneMap(ctx.funcStore),
|
funcStore: CloneMap(ctx.funcStore),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctx *SimpleFuncStore) GetFuncInfo(name string) (info exprFunc) {
|
func (ctx *SimpleFuncStore) GetFuncInfo(name string) (info ExprFunc) {
|
||||||
info, _ = ctx.funcStore[name]
|
info, _ = ctx.funcStore[name]
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -11,7 +11,7 @@ func NewSimpleVarStore() *SimpleVarStore {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctx *SimpleVarStore) Clone() (clone exprContext) {
|
func (ctx *SimpleVarStore) Clone() (clone ExprContext) {
|
||||||
clone = &SimpleVarStore{
|
clone = &SimpleVarStore{
|
||||||
varStore: CloneMap(ctx.varStore),
|
varStore: CloneMap(ctx.varStore),
|
||||||
}
|
}
|
||||||
@ -41,7 +41,7 @@ func (ctx *SimpleVarStore) EnumVars(acceptor func(name string) (accept bool)) (v
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctx *SimpleVarStore) GetFuncInfo(name string) (f exprFunc) {
|
func (ctx *SimpleVarStore) GetFuncInfo(name string) (f ExprFunc) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
8
term.go
8
term.go
@ -58,7 +58,7 @@ const (
|
|||||||
posMultifix
|
posMultifix
|
||||||
)
|
)
|
||||||
|
|
||||||
type evalFuncType func(ctx exprContext, self *term) (v any, err error)
|
type evalFuncType func(ctx ExprContext, self *term) (v any, err error)
|
||||||
|
|
||||||
// type iterm interface {
|
// type iterm interface {
|
||||||
// getClass() termClass
|
// getClass() termClass
|
||||||
@ -167,7 +167,7 @@ func (self *term) value() any {
|
|||||||
return self.tk.Value
|
return self.tk.Value
|
||||||
}
|
}
|
||||||
|
|
||||||
func (self *term) compute(ctx exprContext) (v any, err error) {
|
func (self *term) compute(ctx ExprContext) (v any, err error) {
|
||||||
if self.evalFunc == nil {
|
if self.evalFunc == nil {
|
||||||
err = self.tk.Errorf("undefined eval-func for %v term type", self.kind)
|
err = self.tk.Errorf("undefined eval-func for %v term type", self.kind)
|
||||||
} else {
|
} else {
|
||||||
@ -225,7 +225,7 @@ func (self *term) anyChildrenNil() bool {
|
|||||||
}
|
}
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
func (self *term) evalInfix(ctx exprContext) (leftValue, rightValue any, err error) {
|
func (self *term) evalInfix(ctx ExprContext) (leftValue, rightValue any, err error) {
|
||||||
if err = self.checkOperands(); err == nil {
|
if err = self.checkOperands(); err == nil {
|
||||||
if leftValue, err = self.children[0].compute(ctx); err == nil {
|
if leftValue, err = self.children[0].compute(ctx); err == nil {
|
||||||
rightValue, err = self.children[1].compute(ctx)
|
rightValue, err = self.children[1].compute(ctx)
|
||||||
@ -234,7 +234,7 @@ func (self *term) evalInfix(ctx exprContext) (leftValue, rightValue any, err err
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func (self *term) evalPrefix(ctx exprContext) (rightValue any, err error) {
|
func (self *term) evalPrefix(ctx ExprContext) (rightValue any, err error) {
|
||||||
if err = self.checkOperands(); err == nil {
|
if err = self.checkOperands(); err == nil {
|
||||||
rightValue, err = self.children[0].compute(ctx)
|
rightValue, err = self.children[0].compute(ctx)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user