Skip to content

Commit ca4b1ed

Browse files
committed
iterv2: add fast paths to InterleavingIter
Add some fast paths when there is no span iterator, avoiding extra function calls.
1 parent 2722c6e commit ca4b1ed

1 file changed

Lines changed: 31 additions & 14 deletions

File tree

internal/iterv2/interleaving_iter.go

Lines changed: 31 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -242,8 +242,6 @@ func (i *InterleavingIter) emitBoundary(userKey []byte) *base.InternalKV {
242242
// inSpan is true, pos is inside span.
243243
func (i *InterleavingIter) positionSpanIterForward(pos []byte, flags base.SeekGEFlags) {
244244
if i.spanIter == nil {
245-
i.inSpan = false
246-
i.span = nil
247245
i.computeCurrentSpan()
248246
return
249247
}
@@ -288,8 +286,6 @@ func (i *InterleavingIter) nextSpan(s *keyspan.Span, err error) {
288286
// inSpan is true, pos is inside span (or touching the end of the span).
289287
func (i *InterleavingIter) positionSpanIterBackward(pos []byte) {
290288
if i.spanIter == nil {
291-
i.span = nil
292-
i.inSpan = false
293289
i.computeCurrentSpan()
294290
return
295291
}
@@ -380,6 +376,11 @@ func (i *InterleavingIter) seekGEHelper(
380376
i.exhaust()
381377
return nil
382378
}
379+
} else if i.spanIter == nil {
380+
// Fast path.
381+
i.presentedSpan.BoundaryType = BoundaryEnd
382+
i.presentedSpan.Boundary = i.effectiveUpper() // can be nil
383+
return kv
383384
}
384385
i.positionSpanIterForward(key, flags)
385386
r := i.resolveForward()
@@ -425,6 +426,11 @@ func (i *InterleavingIter) SeekPrefixGE(
425426
i.exhaust()
426427
return nil
427428
}
429+
} else if i.spanIter == nil {
430+
// Fast path.
431+
i.presentedSpan.BoundaryType = BoundaryEnd
432+
i.presentedSpan.Boundary = i.effectiveUpper() // can be nil
433+
return kv
428434
}
429435
i.positionSpanIterForward(key, flags)
430436
return i.resolveForward()
@@ -476,20 +482,23 @@ func (i *InterleavingIter) First() *base.InternalKV {
476482
i.setError(err)
477483
return nil
478484
}
479-
}
480-
481-
if i.pointKV == nil && i.geUpper(i.startKey) {
482-
// Empty range.
483-
i.exhaust()
484-
return nil
485+
if i.geUpper(i.startKey) {
486+
// Empty range.
487+
i.exhaust()
488+
return nil
489+
}
485490
}
486491

487492
if i.spanIter != nil {
488493
i.nextSpan(i.spanIter.First())
489494
i.inSpan = i.span != nil && i.leEffectiveLower(i.span.Start)
490495
} else {
491-
i.span = nil
492-
i.inSpan = false
496+
if i.pointKV != nil {
497+
// Fast path.
498+
i.presentedSpan.BoundaryType = BoundaryEnd
499+
i.presentedSpan.Boundary = i.effectiveUpper() // can be nil
500+
return i.pointKV
501+
}
493502
}
494503
i.computeCurrentSpan()
495504
return i.resolveForward()
@@ -552,8 +561,16 @@ func (i *InterleavingIter) Next() *base.InternalKV {
552561
i.setError(err)
553562
return nil
554563
}
555-
} else if invariants.Enabled && i.prefix != nil && !i.cmp.HasPrefix(i.pointKV.K.UserKey, i.prefix) {
556-
panic(errors.AssertionFailedf("pointIter %T did not enforce strict prefix iteration", i.pointIter))
564+
} else {
565+
if invariants.Enabled && i.prefix != nil && !i.cmp.HasPrefix(i.pointKV.K.UserKey, i.prefix) {
566+
panic(errors.AssertionFailedf("pointIter %T did not enforce strict prefix iteration", i.pointIter))
567+
}
568+
if i.spanIter == nil {
569+
// Fast path.
570+
i.presentedSpan.BoundaryType = BoundaryEnd
571+
i.presentedSpan.Boundary = i.effectiveUpper() // can be nil
572+
return i.pointKV
573+
}
557574
}
558575
// If pointKV is outside the current span, we will emit a boundary in
559576
// resolveForward.

0 commit comments

Comments
 (0)