Add readTypeOfValue (#3728)

This improves csv-import a bit since it allows us to skip allocation of
values in the struct when we only want the type.
This commit is contained in:
Erik Arvidsson
2017-09-20 16:46:19 -07:00
committed by GitHub
parent 66ae5574e3
commit 72da69ebce
3 changed files with 42 additions and 3 deletions

View File

@@ -121,8 +121,7 @@ func (seq leafSequence) typeOf() *Type {
count := dec.readCount()
ts := make([]*Type, count)
for i := uint64(0); i < count; i++ {
v := dec.readValue()
ts[i] = v.typeOf()
ts[i] = dec.readTypeOfValue()
}
return makeCompoundType(kind, makeCompoundType(UnionKind, ts...))
}

View File

@@ -159,6 +159,10 @@ func (s Struct) WalkRefs(cb RefCallback) {
func (s Struct) typeOf() *Type {
dec := s.decoder()
return readStructTypeOfValue(&dec)
}
func readStructTypeOfValue(dec *valueDecoder) *Type {
dec.skipKind()
name := dec.readString()
count := dec.readCount()
@@ -167,7 +171,7 @@ func (s Struct) typeOf() *Type {
typeFields[i] = StructField{
Name: dec.readString(),
Optional: false,
Type: dec.readValue().typeOf(),
Type: dec.readTypeOfValue(),
}
}
return makeStructTypeQuickly(name, typeFields)

View File

@@ -348,6 +348,42 @@ func (r *valueDecoder) skipValue() {
}
}
// readTypeOfValue is basically readValue().typeOf() but it ensures that we do
// not allocate values where we do not need to.
func (r *valueDecoder) readTypeOfValue() *Type {
k := r.peekKind()
switch k {
case BlobKind:
r.skipBlob()
return BlobType
case BoolKind:
r.skipKind()
r.skipBool()
return BoolType
case NumberKind:
r.skipKind()
r.skipNumber()
return NumberType
case StringKind:
r.skipKind()
r.skipString()
return StringType
case ListKind, MapKind, RefKind, SetKind:
// These do not decode the actual values anyway.
return r.readValue().typeOf()
case StructKind:
return readStructTypeOfValue(r)
case TypeKind:
r.skipKind()
r.skipType()
return TypeType
case CycleKind, UnionKind, ValueKind:
d.Panic("A value instance can never have type %s", k)
}
panic("not reachable")
}
func (r *valueDecoder) copyValue(w nomsWriter) {
start := r.pos()
r.skipValue()