aboutsummaryrefslogtreecommitdiff
path: root/evaluator.go
diff options
context:
space:
mode:
Diffstat (limited to 'evaluator.go')
-rw-r--r--evaluator.go51
1 files changed, 51 insertions, 0 deletions
diff --git a/evaluator.go b/evaluator.go
new file mode 100644
index 0000000..486d45f
--- /dev/null
+++ b/evaluator.go
@@ -0,0 +1,51 @@
+package expression
+
+import (
+ "go/scanner"
+ "go/token"
+)
+
+type Evaluator struct {
+ operators map[token.Token]Operator
+ functions map[string]func(stack *Stack) error
+}
+
+func New() *Evaluator {
+ return &Evaluator{
+ operators: DefaultOperators,
+ functions: DefaultFunctions,
+ }
+}
+
+func (e *Evaluator) Eval(expression string) (any, error) {
+ s := scanner.Scanner{}
+ fset := token.NewFileSet()
+ file := fset.AddFile("", fset.Base(), len(expression))
+ s.Init(file, []byte(expression), nil, scanner.ScanComments)
+ tokens := make(chan Token)
+ go func() {
+ for {
+ pos, tok, lit := s.Scan()
+ if tok == token.SEMICOLON {
+ continue
+ }
+ if tok == token.EOF {
+ break
+ }
+ tokens <- Token{
+ Token: tok,
+ Literal: lit,
+ Pos: int(pos),
+ }
+ }
+ close(tokens)
+ }()
+ rpnTokens := e.ToPRN(tokens)
+ return e.execute(rpnTokens)
+}
+
+type Operator struct {
+ fn func(stack *Stack) error
+ priority int
+ isLeftAssoc bool
+}