improved usability of the list iterator

This commit is contained in:
Celestino Amoroso 2024-05-03 06:26:17 +02:00
parent dc9eca83e8
commit 360ebce015
5 changed files with 53 additions and 31 deletions

View File

@ -30,7 +30,7 @@ func importGeneral(ctx ExprContext, name string, args []any) (result any, err er
dirList = addEnvImportDirs(dirList)
dirList = addPresetImportDirs(ctx, dirList)
result, err = doImport(ctx, name, dirList, NewFlatArrayIterator(args))
result, err = doImport(ctx, name, dirList, NewArrayIterator(args))
return
}

View File

@ -37,8 +37,8 @@ func doAdd(ctx ExprContext, name string, it Iterator) (result any, err error) {
if err = checkNumberParamExpected(name, v, it.Index()); err != nil {
break
}
if array, ok := v.(*ListType); ok {
if v, err = doAdd(ctx, name, NewFlatArrayIterator(*array)); err != nil {
if list, ok := v.(*ListType); ok {
if v, err = doAdd(ctx, name, NewListIterator(list)); err != nil {
break
}
}
@ -87,7 +87,7 @@ func doAdd(ctx ExprContext, name string, it Iterator) (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, NewArrayIterator(args))
return
}
@ -113,8 +113,8 @@ func doMul(ctx ExprContext, name string, it Iterator) (result any, err error) {
break
}
if array, ok := v.(*ListType); ok {
if v, err = doMul(ctx, name, NewFlatArrayIterator(*array)); err != nil {
if list, ok := v.(*ListType); ok {
if v, err = doMul(ctx, name, NewListIterator(list)); err != nil {
break
}
}
@ -163,7 +163,7 @@ func doMul(ctx ExprContext, name string, it Iterator) (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, NewArrayIterator(args))
return
}

View File

@ -39,15 +39,15 @@ func joinStrFunc(ctx ExprContext, name string, args []any) (result any, err erro
if len(args) == 1 {
result = ""
} else if len(args) == 2 {
if ls, ok := args[1].([]any); ok {
result, err = doJoinStr(name, sep, NewFlatArrayIterator(ls))
if ls, ok := args[1].(*ListType); ok {
result, err = doJoinStr(name, sep, NewListIterator(ls))
} else if it, ok := args[1].(Iterator); ok {
result, err = doJoinStr(name, sep, it)
} else {
err = errInvalidParameterValue(name, paramParts, args[1])
}
} else {
result, err = doJoinStr(name, sep, NewFlatArrayIterator(args[1:]))
result, err = doJoinStr(name, sep, NewArrayIterator(args[1:]))
}
} else {
err = errWrongParamType(name, paramSeparator, typeString, args[0])

View File

@ -6,33 +6,53 @@ package expr
import "io"
type FlatArrayIterator struct {
a ListType
type ListIterator struct {
a *ListType
index int
}
func NewFlatArrayIterator(array ListType) *FlatArrayIterator {
return &FlatArrayIterator{a: array, index: 0}
func NewListIterator(list *ListType) *ListIterator {
return &ListIterator{a: list, index: 0}
}
func (it *FlatArrayIterator) HasOperation(name string) bool {
func NewArrayIterator(array []any) *ListIterator {
return &ListIterator{a: (*ListType)(&array), index: 0}
}
func NewAnyIterator(value any) (it *ListIterator) {
if value == nil {
it = NewArrayIterator([]any{})
} else if list, ok := value.(*ListType); ok {
it = NewListIterator(list)
} else if array, ok := value.([]any); ok {
it = NewArrayIterator(array)
} else if it1, ok := value.(*ListIterator); ok {
it = it1
} else {
it = NewArrayIterator([]any{value})
}
return
}
func (it *ListIterator) HasOperation(name string) bool {
return false
}
func (it *FlatArrayIterator) CallOperation(name string, args []any) (any, error) {
func (it *ListIterator) CallOperation(name string, args []any) (any, error) {
return nil, errNoOperation(name)
}
func (it *FlatArrayIterator) Current() (item any, err error) {
if it.index >= 0 && it.index < len(it.a) {
item = it.a[it.index]
func (it *ListIterator) Current() (item any, err error) {
a := *(it.a)
if it.index >= 0 && it.index < len(a) {
item = a[it.index]
} else {
err = io.EOF
}
return
}
func (it *FlatArrayIterator) Next() (item any, err error) {
func (it *ListIterator) Next() (item any, err error) {
if item, err = it.Current(); err != io.EOF {
it.index++
}
@ -45,6 +65,6 @@ func (it *FlatArrayIterator) Next() (item any, err error) {
return
}
func (it *FlatArrayIterator) Index() int {
func (it *ListIterator) Index() int {
return it.index - 1
}

View File

@ -4,6 +4,8 @@
// operator-builtin.go
package expr
import "io"
//-------- builtin term
func newBuiltinTerm(tk *Token) (inst *term) {
@ -18,17 +20,19 @@ func newBuiltinTerm(tk *Token) (inst *term) {
func evalBuiltin(ctx ExprContext, self *term) (v any, err error) {
var childValue any
var it Iterator
if childValue, err = self.evalPrefix(ctx); err != nil {
return
}
count := 0
if isList(childValue) {
list, _ := childValue.(*ListType)
it := NewFlatArrayIterator(*list)
for moduleSpec, err1 := it.Next(); err1 == nil; moduleSpec, err1 = it.Next() {
if isString(childValue) {
module, _ := childValue.(string)
count, err = ImportInContextByGlobPattern(ctx, module)
} else {
var moduleSpec any
it := NewAnyIterator(childValue)
for moduleSpec, err = it.Next(); err == nil; moduleSpec, err = it.Next() {
if module, ok := moduleSpec.(string); ok {
if ImportInContext(ctx, module) {
count++
@ -41,11 +45,9 @@ func evalBuiltin(ctx ExprContext, self *term) (v any, err error) {
break
}
}
} else if isString(childValue) {
module, _ := childValue.(string)
count, err = ImportInContextByGlobPattern(ctx, module)
} else {
err = self.errIncompatibleType(childValue)
if err == io.EOF {
err = nil
}
}
if err == nil {
v = count