-
Notifications
You must be signed in to change notification settings - Fork 66
/
iter.go
52 lines (47 loc) · 1.28 KB
/
iter.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
package zcode
import (
"encoding/binary"
"fmt"
)
// Iter iterates over the sequence of values encoded in Bytes.
type Iter Bytes
// Done returns true if no values remain.
func (i *Iter) Done() bool {
return len(*i) == 0
}
// Next returns the body of the next value along with a boolean that is true if
// the value is a container. It returns an empty slice for an empty or
// zero-length value and nil for a Zed null value. The container boolean is not
// meaningful if the returned Bytes slice is nil. Next panics if the next value
// is malformed.
func (i *Iter) Next() Bytes {
// The tag is zero for a null value; otherwise, it is the value's
// length plus one.
u64, n := binary.Uvarint(*i)
if n <= 0 {
panic(fmt.Sprintf("bad uvarint: %d", n))
}
if tagIsNull(u64) {
*i = (*i)[n:]
return nil
}
end := n + tagLength(u64)
val := (*i)[n:end]
*i = (*i)[end:]
return Bytes(val)
}
// NextTagAndBody returns the next value as a slice containing the value's
// undecoded tag followed by its body. NextTagAndBody panics if the next
// value is malformed.
func (i *Iter) NextTagAndBody() Bytes {
u64, n := binary.Uvarint(*i)
if n <= 0 {
panic(fmt.Sprintf("bad uvarint: %d", n))
}
if !tagIsNull(u64) {
n += tagLength(u64)
}
val := (*i)[:n]
*i = (*i)[n:]
return Bytes(val)
}