diff --git a/common/ptr/ptr.go b/common/ptr/ptr.go index 30a8efe..9315228 100644 --- a/common/ptr/ptr.go +++ b/common/ptr/ptr.go @@ -13,6 +13,7 @@ type Ptr[V any] interface { Set(V) Ptr[V] Size() int Started() bool + Advance(int) Ptr[V] Seek(int) Ptr[V] Reset() Ptr[V] Clone() Ptr[V] diff --git a/common/ptr/scalar.go b/common/ptr/scalar.go index 4171dcd..5576b56 100644 --- a/common/ptr/scalar.go +++ b/common/ptr/scalar.go @@ -67,6 +67,17 @@ func (p *acc[V]) Started() bool { return p.started } +func (p *acc[V]) Advance(i int) Ptr[V] { + if i == 0 { + return p + } + if p.started && i > 0 { + return nil + } + p.started = i >= 0 + return p +} + func (p *acc[V]) Seek(i int) Ptr[V] { p.started = true return p diff --git a/common/ptr/slice.go b/common/ptr/slice.go index d8b5577..5d596d2 100644 --- a/common/ptr/slice.go +++ b/common/ptr/slice.go @@ -68,6 +68,19 @@ func (p *sptr[V]) Started() bool { return p.offset >= 0 } +func (p *sptr[V]) Advance(i int) Ptr[V] { + p.offset += i + l := len(*p.seq) + if p.offset >= l { + p.offset = l - 1 + return nil + } + if p.offset < -1 { + p.offset = -1 + } + return p +} + func (p *sptr[V]) Seek(i int) Ptr[V] { p.offset = i return p diff --git a/tests/common_test.go b/tests/common_test.go index 4eb531c..4ce3a40 100644 --- a/tests/common_test.go +++ b/tests/common_test.go @@ -119,6 +119,8 @@ func PtrSliceTest(t *testing.T) { t.AssertEqual(sp1.Value(), 99) sp1.Next() t.AssertEqual(sp1.Value(), 12) + sp1.Advance(-1) + t.AssertEqual(sp1.Value(), 99) sp1.Reset() t.AssertEqual(sp1.Next().Value(), 11) }