mirror of
https://github.com/nspcc-dev/neo-go.git
synced 2024-11-26 19:42:23 +00:00
vm: add IterBack to the Stack to iterate bottom-to-top
And use it to build user-facing stack representation because that's the order that C# VM uses.
This commit is contained in:
parent
f3ed91a1f7
commit
05f3329ec0
3 changed files with 43 additions and 5 deletions
|
@ -35,7 +35,7 @@ func appendToItems(items *[]stackItem, val StackItem, seen map[StackItem]bool) {
|
||||||
func stackToArray(s *Stack) []stackItem {
|
func stackToArray(s *Stack) []stackItem {
|
||||||
items := make([]stackItem, 0, s.Len())
|
items := make([]stackItem, 0, s.Len())
|
||||||
seen := make(map[StackItem]bool)
|
seen := make(map[StackItem]bool)
|
||||||
s.Iter(func(e *Element) {
|
s.IterBack(func(e *Element) {
|
||||||
appendToItems(&items, e.value, seen)
|
appendToItems(&items, e.value, seen)
|
||||||
})
|
})
|
||||||
return items
|
return items
|
||||||
|
|
|
@ -360,6 +360,17 @@ func (s *Stack) Iter(f func(*Element)) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// IterBack iterates over all the elements of the stack, starting from the bottom
|
||||||
|
// of the stack.
|
||||||
|
// s.IterBack(func(elem *Element) {
|
||||||
|
// // do something with the element.
|
||||||
|
// })
|
||||||
|
func (s *Stack) IterBack(f func(*Element)) {
|
||||||
|
for e := s.Back(); e != nil; e = e.Prev() {
|
||||||
|
f(e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// popSigElements pops keys or signatures from the stack as needed for
|
// popSigElements pops keys or signatures from the stack as needed for
|
||||||
// CHECKMULTISIG.
|
// CHECKMULTISIG.
|
||||||
func (s *Stack) popSigElements() ([][]byte, error) {
|
func (s *Stack) popSigElements() ([][]byte, error) {
|
||||||
|
|
|
@ -154,19 +154,46 @@ func TestIterAfterRemove(t *testing.T) {
|
||||||
|
|
||||||
func TestIteration(t *testing.T) {
|
func TestIteration(t *testing.T) {
|
||||||
var (
|
var (
|
||||||
|
n = 10
|
||||||
s = NewStack("test")
|
s = NewStack("test")
|
||||||
elems = makeElements(10)
|
elems = makeElements(n)
|
||||||
)
|
)
|
||||||
for _, elem := range elems {
|
for _, elem := range elems {
|
||||||
s.Push(elem)
|
s.Push(elem)
|
||||||
}
|
}
|
||||||
assert.Equal(t, len(elems), s.Len())
|
assert.Equal(t, len(elems), s.Len())
|
||||||
|
|
||||||
i := 0
|
iteratedElems := make([]*Element, 0)
|
||||||
|
|
||||||
s.Iter(func(elem *Element) {
|
s.Iter(func(elem *Element) {
|
||||||
i++
|
iteratedElems = append(iteratedElems, elem)
|
||||||
})
|
})
|
||||||
assert.Equal(t, len(elems), i)
|
// Top to bottom order of iteration.
|
||||||
|
poppedElems := make([]*Element, 0)
|
||||||
|
for elem := s.Pop(); elem != nil; elem = s.Pop() {
|
||||||
|
poppedElems = append(poppedElems, elem)
|
||||||
|
}
|
||||||
|
assert.Equal(t, poppedElems, iteratedElems)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBackIteration(t *testing.T) {
|
||||||
|
var (
|
||||||
|
n = 10
|
||||||
|
s = NewStack("test")
|
||||||
|
elems = makeElements(n)
|
||||||
|
)
|
||||||
|
for _, elem := range elems {
|
||||||
|
s.Push(elem)
|
||||||
|
}
|
||||||
|
assert.Equal(t, len(elems), s.Len())
|
||||||
|
|
||||||
|
iteratedElems := make([]*Element, 0)
|
||||||
|
|
||||||
|
s.IterBack(func(elem *Element) {
|
||||||
|
iteratedElems = append(iteratedElems, elem)
|
||||||
|
})
|
||||||
|
// Bottom to the top order of iteration.
|
||||||
|
assert.Equal(t, elems, iteratedElems)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestPushVal(t *testing.T) {
|
func TestPushVal(t *testing.T) {
|
||||||
|
|
Loading…
Reference in a new issue