如何计算整数中的字节数

时间:2016-06-23 19:06:55

标签: go

我有以下变量:

var foo int8
var bar [5]int8

我想计算两个变量中的字节数并输出总和 - 所以在这里它应该是1 + 5 = 6。这可能吗?

2 个答案:

答案 0 :(得分:2)

您可以使用reflect.Size,由于某种原因会返回uintptr,但实际上与unsafe.SizeOf完全相同,而不必使用unsafe

var x [8]byte

t := reflect.TypeOf(x)

fmt.Println(t.Size())

障碍将是地图,切片,字符串和指针,您将获得标头/元数据的大小(或指针的指针大小)。如果那没关系,太好了!如果没有,你可以通过各种方式解决这个问题,这是我最好的选择:

func UnderlyingSize(x interface{}) uintptr {
    v := reflect.ValueOf(x)
    t := v.Type()

    var size uintptr;

    switch t.Kind() {
    // For the builtin collections, we just multiply the len by the
    // element size, for maps also do the key
    case reflect.Map:
         l := uintptr(v.Len())
        size = t.Key().Size()*l + t.Elem().Size()*l
    case reflect.Slice:
        t := t.Elem();
        size = t.Size() * uintptr(v.Len())
    case reflect.Ptr:
        t := t.Elem();
        size = t.Size()
    // Strings are just byte arrays, so it's just the len
    case reflect.String:
        size = uintptr(v.Len())
    // For an interface, we need to find the underlying type
    case reflect.Interface:
        v := v.Elem()
        size = UnderlyingSize(v)
    // For anything else, including arrays, Size returns the correct value
    default:
        size = t.Size();
    }

    return size
}

使用Cap而不是Len会有争议,但它很容易改变自己。如果您想要标题信息的大小和基础大小,也可以将t.Size()添加到这些值中的任何一个。请注意一个警告,即真正的map可能需要更多的内存而不仅仅是键+值+标题大小,因为可能还有一些额外的信息。

如果你的数据结构是一个集合,你必须自己实现这样的东西,但如果它是一个简单的结构(即只由POD结构和内置类型组成),您只需添加所有成员的UnderlyingSize即可。

答案 1 :(得分:1)

您可以使用unsafe.Sizeofhttps://play.golang.org/p/FroasKud7I):

unsafe.Sizeof(foo) + unsafe.Sizeof(bar)