@@ -14,21 +14,24 @@ import (
1414// cache shadows (overrides) the parent.
1515//
1616// TODO: Optimize by memoizing.
17- type cacheMergeIterator struct {
18- parent types.Iterator
19- cache types.Iterator
17+ type cacheMergeIterator [ V any ] struct {
18+ parent types.GIterator [ V ]
19+ cache types.GIterator [ V ]
2020 ascending bool
2121
2222 valid bool
23+
24+ isZero func (V ) bool
2325}
2426
25- var _ types.Iterator = (* cacheMergeIterator )(nil )
27+ var _ types.Iterator = (* cacheMergeIterator [[] byte ] )(nil )
2628
27- func NewCacheMergeIterator (parent , cache types.Iterator , ascending bool ) types.Iterator {
28- iter := & cacheMergeIterator {
29+ func NewCacheMergeIterator [ V any ] (parent , cache types.GIterator [ V ] , ascending bool , isZero func ( V ) bool ) types.GIterator [ V ] {
30+ iter := & cacheMergeIterator [ V ] {
2931 parent : parent ,
3032 cache : cache ,
3133 ascending : ascending ,
34+ isZero : isZero ,
3235 }
3336
3437 iter .valid = iter .skipUntilExistsOrInvalid ()
@@ -37,17 +40,17 @@ func NewCacheMergeIterator(parent, cache types.Iterator, ascending bool) types.I
3740
3841// Domain implements Iterator.
3942// Returns parent domain because cache and parent domains are the same.
40- func (iter * cacheMergeIterator ) Domain () (start , end []byte ) {
43+ func (iter * cacheMergeIterator [ V ] ) Domain () (start , end []byte ) {
4144 return iter .parent .Domain ()
4245}
4346
4447// Valid implements Iterator.
45- func (iter * cacheMergeIterator ) Valid () bool {
48+ func (iter * cacheMergeIterator [ V ] ) Valid () bool {
4649 return iter .valid
4750}
4851
4952// Next implements Iterator
50- func (iter * cacheMergeIterator ) Next () {
53+ func (iter * cacheMergeIterator [ V ] ) Next () {
5154 iter .assertValid ()
5255
5356 switch {
@@ -74,7 +77,7 @@ func (iter *cacheMergeIterator) Next() {
7477}
7578
7679// Key implements Iterator
77- func (iter * cacheMergeIterator ) Key () []byte {
80+ func (iter * cacheMergeIterator [ V ] ) Key () []byte {
7881 iter .assertValid ()
7982
8083 // If parent is invalid, get the cache key.
@@ -104,7 +107,7 @@ func (iter *cacheMergeIterator) Key() []byte {
104107}
105108
106109// Value implements Iterator
107- func (iter * cacheMergeIterator ) Value () [] byte {
110+ func (iter * cacheMergeIterator [ V ] ) Value () V {
108111 iter .assertValid ()
109112
110113 // If parent is invalid, get the cache value.
@@ -134,7 +137,7 @@ func (iter *cacheMergeIterator) Value() []byte {
134137}
135138
136139// Close implements Iterator
137- func (iter * cacheMergeIterator ) Close () error {
140+ func (iter * cacheMergeIterator [ V ] ) Close () error {
138141 err1 := iter .cache .Close ()
139142 if err := iter .parent .Close (); err != nil {
140143 return err
@@ -145,7 +148,7 @@ func (iter *cacheMergeIterator) Close() error {
145148
146149// Error returns an error if the cacheMergeIterator is invalid defined by the
147150// Valid method.
148- func (iter * cacheMergeIterator ) Error () error {
151+ func (iter * cacheMergeIterator [ V ] ) Error () error {
149152 if ! iter .Valid () {
150153 return errors .New ("invalid cacheMergeIterator" )
151154 }
@@ -155,14 +158,14 @@ func (iter *cacheMergeIterator) Error() error {
155158
156159// If not valid, panics.
157160// NOTE: May have side-effect of iterating over cache.
158- func (iter * cacheMergeIterator ) assertValid () {
161+ func (iter * cacheMergeIterator [ V ] ) assertValid () {
159162 if err := iter .Error (); err != nil {
160163 panic (err )
161164 }
162165}
163166
164167// Like bytes.Compare but opposite if not ascending.
165- func (iter * cacheMergeIterator ) compare (a , b []byte ) int {
168+ func (iter * cacheMergeIterator [ V ] ) compare (a , b []byte ) int {
166169 if iter .ascending {
167170 return bytes .Compare (a , b )
168171 }
@@ -175,9 +178,9 @@ func (iter *cacheMergeIterator) compare(a, b []byte) int {
175178// If the current cache item is not a delete item, does nothing.
176179// If `until` is nil, there is no limit, and cache may end up invalid.
177180// CONTRACT: cache is valid.
178- func (iter * cacheMergeIterator ) skipCacheDeletes (until []byte ) {
181+ func (iter * cacheMergeIterator [ V ] ) skipCacheDeletes (until []byte ) {
179182 for iter .cache .Valid () &&
180- iter .cache .Value () == nil &&
183+ iter .isZero ( iter . cache .Value ()) &&
181184 (until == nil || iter .compare (iter .cache .Key (), until ) < 0 ) {
182185 iter .cache .Next ()
183186 }
@@ -186,7 +189,7 @@ func (iter *cacheMergeIterator) skipCacheDeletes(until []byte) {
186189// Fast forwards cache (or parent+cache in case of deleted items) until current
187190// item exists, or until iterator becomes invalid.
188191// Returns whether the iterator is valid.
189- func (iter * cacheMergeIterator ) skipUntilExistsOrInvalid () bool {
192+ func (iter * cacheMergeIterator [ V ] ) skipUntilExistsOrInvalid () bool {
190193 for {
191194 // If parent is invalid, fast-forward cache.
192195 if ! iter .parent .Valid () {
@@ -211,7 +214,7 @@ func (iter *cacheMergeIterator) skipUntilExistsOrInvalid() bool {
211214 case 0 : // parent == cache.
212215 // Skip over if cache item is a delete.
213216 valueC := iter .cache .Value ()
214- if valueC == nil {
217+ if iter . isZero ( valueC ) {
215218 iter .parent .Next ()
216219 iter .cache .Next ()
217220
@@ -223,7 +226,7 @@ func (iter *cacheMergeIterator) skipUntilExistsOrInvalid() bool {
223226 case 1 : // cache < parent
224227 // Skip over if cache item is a delete.
225228 valueC := iter .cache .Value ()
226- if valueC == nil {
229+ if iter . isZero ( valueC ) {
227230 iter .skipCacheDeletes (keyP )
228231 continue
229232 }
0 commit comments