This is an automated email from the ASF dual-hosted git repository.

kou pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/arrow.git


The following commit(s) were added to refs/heads/master by this push:
     new c41b71d98c ARROW-16556: [Go] Add Layout method to DataTypes (#13136)
c41b71d98c is described below

commit c41b71d98caff65d6dbe26c51d2c3689ea908c29
Author: Matt Topol <[email protected]>
AuthorDate: Wed Jun 1 21:40:30 2022 -0400

    ARROW-16556: [Go] Add Layout method to DataTypes (#13136)
    
    Lead-authored-by: Matt Topol <[email protected]>
    Co-authored-by: Matthew Topol <[email protected]>
    Signed-off-by: Sutou Kouhei <[email protected]>
---
 go/arrow/array/array_test.go          |  9 +++--
 go/arrow/datatype.go                  | 75 +++++++++++++++++++++++++++++++++++
 go/arrow/datatype_binary.go           |  8 ++++
 go/arrow/datatype_extension.go        |  2 +
 go/arrow/datatype_fixedwidth.go       | 49 +++++++++++++++++++++++
 go/arrow/datatype_nested.go           | 16 ++++++++
 go/arrow/datatype_null.go             |  3 ++
 go/arrow/datatype_numeric.gen.go      | 48 ++++++++++++++++++++++
 go/arrow/datatype_numeric.gen.go.tmpl |  4 ++
 9 files changed, 210 insertions(+), 4 deletions(-)

diff --git a/go/arrow/array/array_test.go b/go/arrow/array/array_test.go
index d39bcfa115..7820218aab 100644
--- a/go/arrow/array/array_test.go
+++ b/go/arrow/array/array_test.go
@@ -31,10 +31,11 @@ type testDataType struct {
        id arrow.Type
 }
 
-func (d *testDataType) ID() arrow.Type      { return d.id }
-func (d *testDataType) Name() string        { panic("implement me") }
-func (d *testDataType) BitWidth() int       { return 8 }
-func (d *testDataType) Fingerprint() string { return "" }
+func (d *testDataType) ID() arrow.Type            { return d.id }
+func (d *testDataType) Name() string              { panic("implement me") }
+func (d *testDataType) BitWidth() int             { return 8 }
+func (d *testDataType) Fingerprint() string       { return "" }
+func (testDataType) Layout() arrow.DataTypeLayout { return 
arrow.DataTypeLayout{} }
 
 func TestMakeFromData(t *testing.T) {
        tests := []struct {
diff --git a/go/arrow/datatype.go b/go/arrow/datatype.go
index dc7a974907..ed6e803aea 100644
--- a/go/arrow/datatype.go
+++ b/go/arrow/datatype.go
@@ -165,6 +165,7 @@ type DataType interface {
        // Name is name of the data type.
        Name() string
        Fingerprint() string
+       Layout() DataTypeLayout
 }
 
 // FixedWidthDataType is the representation of an Arrow type that
@@ -209,3 +210,77 @@ func timeUnitFingerprint(unit TimeUnit) rune {
                return rune(0)
        }
 }
+
+// BufferKind describes the type of buffer expected when defining a layout 
specification
+type BufferKind int8
+
+// The expected types of buffers
+const (
+       KindFixedWidth BufferKind = iota
+       KindVarWidth
+       KindBitmap
+       KindAlwaysNull
+)
+
+// BufferSpec provides a specification for the buffers of a particular datatype
+type BufferSpec struct {
+       Kind      BufferKind
+       ByteWidth int // for KindFixedWidth
+}
+
+func (b BufferSpec) Equals(other BufferSpec) bool {
+       return b.Kind == other.Kind && (b.Kind != KindFixedWidth || b.ByteWidth 
== other.ByteWidth)
+}
+
+// DataTypeLayout represents the physical layout of a datatype's buffers 
including
+// the number of and types of those binary buffers. This will correspond
+// with the buffers in the ArrayData for an array of that type.
+type DataTypeLayout struct {
+       Buffers []BufferSpec
+       HasDict bool
+}
+
+func SpecFixedWidth(w int) BufferSpec { return BufferSpec{KindFixedWidth, w} }
+func SpecVariableWidth() BufferSpec   { return BufferSpec{KindVarWidth, -1} }
+func SpecBitmap() BufferSpec          { return BufferSpec{KindBitmap, -1} }
+func SpecAlwaysNull() BufferSpec      { return BufferSpec{KindAlwaysNull, -1} }
+
+// IsInteger is a helper to return true if the type ID provided is one of the
+// integral types of uint or int with the varying sizes.
+func IsInteger(t Type) bool {
+       switch t {
+       case UINT8, INT8, UINT16, INT16, UINT32, INT32, UINT64, INT64:
+               return true
+       }
+       return false
+}
+
+// IsPrimitive returns true if the provided type ID represents a fixed width
+// primitive type.
+func IsPrimitive(t Type) bool {
+       switch t {
+       case BOOL, UINT8, INT8, UINT16, INT16, UINT32, INT32, UINT64, INT64,
+               FLOAT16, FLOAT32, FLOAT64, DATE32, DATE64, TIME32, TIME64, 
TIMESTAMP,
+               DURATION, INTERVAL_MONTHS, INTERVAL_DAY_TIME, 
INTERVAL_MONTH_DAY_NANO:
+               return true
+       }
+       return false
+}
+
+// IsBaseBinary returns true for Binary/String and their LARGE variants
+func IsBaseBinary(t Type) bool {
+       switch t {
+       case BINARY, STRING, LARGE_BINARY, LARGE_STRING:
+               return true
+       }
+       return false
+}
+
+// IsFixedSizeBinary returns true for Decimal128/256 and FixedSizeBinary
+func IsFixedSizeBinary(t Type) bool {
+       switch t {
+       case DECIMAL128, DECIMAL256, FIXED_SIZE_BINARY:
+               return true
+       }
+       return false
+}
diff --git a/go/arrow/datatype_binary.go b/go/arrow/datatype_binary.go
index 110ef491e4..d77e7a64bd 100644
--- a/go/arrow/datatype_binary.go
+++ b/go/arrow/datatype_binary.go
@@ -23,6 +23,10 @@ func (t *BinaryType) Name() string        { return "binary" }
 func (t *BinaryType) String() string      { return "binary" }
 func (t *BinaryType) binary()             {}
 func (t *BinaryType) Fingerprint() string { return typeFingerprint(t) }
+func (t *BinaryType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(),
+               SpecFixedWidth(Int32SizeBytes), SpecVariableWidth()}}
+}
 
 type StringType struct{}
 
@@ -31,6 +35,10 @@ func (t *StringType) Name() string        { return "utf8" }
 func (t *StringType) String() string      { return "utf8" }
 func (t *StringType) binary()             {}
 func (t *StringType) Fingerprint() string { return typeFingerprint(t) }
+func (t *StringType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(),
+               SpecFixedWidth(Int32SizeBytes), SpecVariableWidth()}}
+}
 
 var (
        BinaryTypes = struct {
diff --git a/go/arrow/datatype_extension.go b/go/arrow/datatype_extension.go
index c03a3716aa..0c1c35c0cb 100644
--- a/go/arrow/datatype_extension.go
+++ b/go/arrow/datatype_extension.go
@@ -162,6 +162,8 @@ func (e *ExtensionBase) Fields() []Field {
        return nil
 }
 
+func (e *ExtensionBase) Layout() DataTypeLayout { return e.Storage.Layout() }
+
 // this no-op exists to ensure that this type must be embedded in any 
user-defined extension type.
 //lint:ignore U1000 this function is intentionally unused as it only exists to 
ensure embedding happens
 func (ExtensionBase) mustEmbedExtensionBase() {}
diff --git a/go/arrow/datatype_fixedwidth.go b/go/arrow/datatype_fixedwidth.go
index c8c9b6d44d..bf64299a6f 100644
--- a/go/arrow/datatype_fixedwidth.go
+++ b/go/arrow/datatype_fixedwidth.go
@@ -35,6 +35,10 @@ func (t *BooleanType) Fingerprint() string { return 
typeFingerprint(t) }
 // BitWidth returns the number of bits required to store a single element of 
this data type in memory.
 func (t *BooleanType) BitWidth() int { return 1 }
 
+func (BooleanType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), SpecBitmap()}}
+}
+
 type FixedSizeBinaryType struct {
        ByteWidth int
 }
@@ -46,6 +50,9 @@ func (t *FixedSizeBinaryType) Fingerprint() string { return 
typeFingerprint(t) }
 func (t *FixedSizeBinaryType) String() string {
        return "fixed_size_binary[" + strconv.Itoa(t.ByteWidth) + "]"
 }
+func (t *FixedSizeBinaryType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(t.ByteWidth)}}
+}
 
 type (
        Timestamp int64
@@ -346,6 +353,10 @@ func (t *TimestampType) Fingerprint() string {
 // BitWidth returns the number of bits required to store a single element of 
this data type in memory.
 func (*TimestampType) BitWidth() int { return 64 }
 
+func (TimestampType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(TimestampSizeBytes)}}
+}
+
 func (t *TimestampType) TimeUnit() TimeUnit { return t.Unit }
 
 // ClearCachedLocation clears the cached time.Location object in the type.
@@ -438,6 +449,10 @@ func (t *Time32Type) Fingerprint() string {
        return typeFingerprint(t) + string(timeUnitFingerprint(t.Unit))
 }
 
+func (Time32Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(Time32SizeBytes)}}
+}
+
 func (t *Time32Type) TimeUnit() TimeUnit { return t.Unit }
 
 // Time64Type is encoded as a 64-bit signed integer, representing either 
microseconds or nanoseconds since midnight.
@@ -453,6 +468,10 @@ func (t *Time64Type) Fingerprint() string {
        return typeFingerprint(t) + string(timeUnitFingerprint(t.Unit))
 }
 
+func (Time64Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(Time64SizeBytes)}}
+}
+
 func (t *Time64Type) TimeUnit() TimeUnit { return t.Unit }
 
 // DurationType is encoded as a 64-bit signed integer, representing an amount
@@ -469,6 +488,10 @@ func (t *DurationType) Fingerprint() string {
        return typeFingerprint(t) + string(timeUnitFingerprint(t.Unit))
 }
 
+func (DurationType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(DurationSizeBytes)}}
+}
+
 func (t *DurationType) TimeUnit() TimeUnit { return t.Unit }
 
 // Float16Type represents a floating point value encoded with a 16-bit 
precision.
@@ -482,6 +505,10 @@ func (t *Float16Type) Fingerprint() string { return 
typeFingerprint(t) }
 // BitWidth returns the number of bits required to store a single element of 
this data type in memory.
 func (t *Float16Type) BitWidth() int { return 16 }
 
+func (Float16Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(Float16SizeBytes)}}
+}
+
 // Decimal128Type represents a fixed-size 128-bit decimal type.
 type Decimal128Type struct {
        Precision int32
@@ -498,6 +525,10 @@ func (t *Decimal128Type) Fingerprint() string {
        return fmt.Sprintf("%s[%d,%d,%d]", typeFingerprint(t), t.BitWidth(), 
t.Precision, t.Scale)
 }
 
+func (Decimal128Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(Decimal128SizeBytes)}}
+}
+
 // MonthInterval represents a number of months.
 type MonthInterval int32
 
@@ -531,6 +562,10 @@ func (*MonthIntervalType) Fingerprint() string { return 
typeIDFingerprint(INTERV
 // BitWidth returns the number of bits required to store a single element of 
this data type in memory.
 func (t *MonthIntervalType) BitWidth() int { return 32 }
 
+func (MonthIntervalType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(MonthIntervalSizeBytes)}}
+}
+
 // DayTimeInterval represents a number of days and milliseconds (fraction of 
day).
 type DayTimeInterval struct {
        Days         int32 `json:"days"`
@@ -549,6 +584,10 @@ func (*DayTimeIntervalType) Fingerprint() string { return 
typeIDFingerprint(INTE
 // BitWidth returns the number of bits required to store a single element of 
this data type in memory.
 func (t *DayTimeIntervalType) BitWidth() int { return 64 }
 
+func (DayTimeIntervalType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(DayTimeIntervalSizeBytes)}}
+}
+
 // MonthDayNanoInterval represents a number of months, days and nanoseconds 
(fraction of day).
 type MonthDayNanoInterval struct {
        Months      int32 `json:"months"`
@@ -571,6 +610,10 @@ func (*MonthDayNanoIntervalType) Fingerprint() string {
 // BitWidth returns the number of bits required to store a single element of 
this data type in memory.
 func (*MonthDayNanoIntervalType) BitWidth() int { return 128 }
 
+func (MonthDayNanoIntervalType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(MonthDayNanoIntervalSizeBytes)}}
+}
+
 type op int8
 
 const (
@@ -650,6 +693,12 @@ func (d *DictionaryType) Fingerprint() string {
        return ordered
 }
 
+func (d *DictionaryType) Layout() DataTypeLayout {
+       layout := d.IndexType.Layout()
+       layout.HasDict = true
+       return layout
+}
+
 var (
        FixedWidthTypes = struct {
                Boolean              FixedWidthDataType
diff --git a/go/arrow/datatype_nested.go b/go/arrow/datatype_nested.go
index ee4a1befc9..108ef82779 100644
--- a/go/arrow/datatype_nested.go
+++ b/go/arrow/datatype_nested.go
@@ -90,6 +90,10 @@ func (t *ListType) ElemField() Field {
 
 func (t *ListType) Fields() []Field { return []Field{t.ElemField()} }
 
+func (ListType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap(), 
SpecFixedWidth(Int32SizeBytes)}}
+}
+
 // FixedSizeListType describes a nested type in which each array slot contains
 // a fixed-size sequence of values, all having the same relative type.
 type FixedSizeListType struct {
@@ -164,6 +168,10 @@ func (t *FixedSizeListType) Fingerprint() string {
 
 func (t *FixedSizeListType) Fields() []Field { return []Field{t.ElemField()} }
 
+func (FixedSizeListType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap()}}
+}
+
 // StructType describes a nested type parameterized by an ordered sequence
 // of relative types, called its fields.
 type StructType struct {
@@ -253,6 +261,10 @@ func (t *StructType) Fingerprint() string {
        return b.String()
 }
 
+func (StructType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecBitmap()}}
+}
+
 type MapType struct {
        value      *ListType
        KeysSorted bool
@@ -313,6 +325,10 @@ func (t *MapType) Fingerprint() string {
 
 func (t *MapType) Fields() []Field { return t.ValueType().Fields() }
 
+func (t *MapType) Layout() DataTypeLayout {
+       return t.value.Layout()
+}
+
 type Field struct {
        Name     string   // Field name
        Type     DataType // The field's data type
diff --git a/go/arrow/datatype_null.go b/go/arrow/datatype_null.go
index 253e6ed49d..61412f3a9d 100644
--- a/go/arrow/datatype_null.go
+++ b/go/arrow/datatype_null.go
@@ -23,6 +23,9 @@ func (*NullType) ID() Type            { return NULL }
 func (*NullType) Name() string        { return "null" }
 func (*NullType) String() string      { return "null" }
 func (*NullType) Fingerprint() string { return typeIDFingerprint(NULL) }
+func (NullType) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{SpecAlwaysNull()}}
+}
 
 var (
        Null *NullType
diff --git a/go/arrow/datatype_numeric.gen.go b/go/arrow/datatype_numeric.gen.go
index d23ff8fd66..dfcdab5924 100644
--- a/go/arrow/datatype_numeric.gen.go
+++ b/go/arrow/datatype_numeric.gen.go
@@ -25,6 +25,10 @@ func (t *Int8Type) Name() string        { return "int8" }
 func (t *Int8Type) String() string      { return "int8" }
 func (t *Int8Type) BitWidth() int       { return 8 }
 func (t *Int8Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Int8Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Int8SizeBytes)}}
+}
 
 type Int16Type struct{}
 
@@ -33,6 +37,10 @@ func (t *Int16Type) Name() string        { return "int16" }
 func (t *Int16Type) String() string      { return "int16" }
 func (t *Int16Type) BitWidth() int       { return 16 }
 func (t *Int16Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Int16Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Int16SizeBytes)}}
+}
 
 type Int32Type struct{}
 
@@ -41,6 +49,10 @@ func (t *Int32Type) Name() string        { return "int32" }
 func (t *Int32Type) String() string      { return "int32" }
 func (t *Int32Type) BitWidth() int       { return 32 }
 func (t *Int32Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Int32Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Int32SizeBytes)}}
+}
 
 type Int64Type struct{}
 
@@ -49,6 +61,10 @@ func (t *Int64Type) Name() string        { return "int64" }
 func (t *Int64Type) String() string      { return "int64" }
 func (t *Int64Type) BitWidth() int       { return 64 }
 func (t *Int64Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Int64Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Int64SizeBytes)}}
+}
 
 type Uint8Type struct{}
 
@@ -57,6 +73,10 @@ func (t *Uint8Type) Name() string        { return "uint8" }
 func (t *Uint8Type) String() string      { return "uint8" }
 func (t *Uint8Type) BitWidth() int       { return 8 }
 func (t *Uint8Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Uint8Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Uint8SizeBytes)}}
+}
 
 type Uint16Type struct{}
 
@@ -65,6 +85,10 @@ func (t *Uint16Type) Name() string        { return "uint16" }
 func (t *Uint16Type) String() string      { return "uint16" }
 func (t *Uint16Type) BitWidth() int       { return 16 }
 func (t *Uint16Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Uint16Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Uint16SizeBytes)}}
+}
 
 type Uint32Type struct{}
 
@@ -73,6 +97,10 @@ func (t *Uint32Type) Name() string        { return "uint32" }
 func (t *Uint32Type) String() string      { return "uint32" }
 func (t *Uint32Type) BitWidth() int       { return 32 }
 func (t *Uint32Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Uint32Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Uint32SizeBytes)}}
+}
 
 type Uint64Type struct{}
 
@@ -81,6 +109,10 @@ func (t *Uint64Type) Name() string        { return "uint64" 
}
 func (t *Uint64Type) String() string      { return "uint64" }
 func (t *Uint64Type) BitWidth() int       { return 64 }
 func (t *Uint64Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Uint64Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Uint64SizeBytes)}}
+}
 
 type Float32Type struct{}
 
@@ -89,6 +121,10 @@ func (t *Float32Type) Name() string        { return 
"float32" }
 func (t *Float32Type) String() string      { return "float32" }
 func (t *Float32Type) BitWidth() int       { return 32 }
 func (t *Float32Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Float32Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Float32SizeBytes)}}
+}
 
 type Float64Type struct{}
 
@@ -97,6 +133,10 @@ func (t *Float64Type) Name() string        { return 
"float64" }
 func (t *Float64Type) String() string      { return "float64" }
 func (t *Float64Type) BitWidth() int       { return 64 }
 func (t *Float64Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Float64Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Float64SizeBytes)}}
+}
 
 type Date32Type struct{}
 
@@ -105,6 +145,10 @@ func (t *Date32Type) Name() string        { return 
"date32" }
 func (t *Date32Type) String() string      { return "date32" }
 func (t *Date32Type) BitWidth() int       { return 32 }
 func (t *Date32Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Date32Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Date32SizeBytes)}}
+}
 
 type Date64Type struct{}
 
@@ -113,6 +157,10 @@ func (t *Date64Type) Name() string        { return 
"date64" }
 func (t *Date64Type) String() string      { return "date64" }
 func (t *Date64Type) BitWidth() int       { return 64 }
 func (t *Date64Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *Date64Type) Layout() DataTypeLayout {
+       return DataTypeLayout{Buffers: []BufferSpec{
+               SpecBitmap(), SpecFixedWidth(Date64SizeBytes)}}
+}
 
 var (
        PrimitiveTypes = struct {
diff --git a/go/arrow/datatype_numeric.gen.go.tmpl 
b/go/arrow/datatype_numeric.gen.go.tmpl
index dd4c92f29b..a784619bd1 100644
--- a/go/arrow/datatype_numeric.gen.go.tmpl
+++ b/go/arrow/datatype_numeric.gen.go.tmpl
@@ -24,6 +24,10 @@ func (t *{{.Name}}Type) Name() string        { return 
"{{.Name|lower}}" }
 func (t *{{.Name}}Type) String() string      { return "{{.Name|lower}}" }
 func (t *{{.Name}}Type) BitWidth() int       { return {{.Size}} }
 func (t *{{.Name}}Type) Fingerprint() string { return typeFingerprint(t) }
+func (t *{{.Name}}Type) Layout() DataTypeLayout { 
+        return DataTypeLayout{Buffers: []BufferSpec{
+                SpecBitmap(), SpecFixedWidth({{.Name}}SizeBytes)}}
+}
 
 {{end}}
 

Reply via email to