go - go中结构的内存分配
问题描述
我最近遇到了http://golang-sizeof.tips/,它解释了如何为结构分配内存。我知道为了确保连续的内存分配,我们在为没有填充的变量分配内存时添加填充将不会获得连续的内存。所以我在我的 64 位计算机上测试了各种组合,发现网站上的结果与我的计算机上的结果不匹配。这是针对这种情况的:
type S2 struct {
a string
b bool
e bool
d int32
f bool
c string
}
总的来说,下面的代码给了我48
变量的大小。
y := S2{"q", true, true,2,true,"w"}
fmt.Println(unsafe.Sizeof(y))
但这与http://golang-sizeof.tips/?t=blahblah的预期不同。为什么会观察到这种行为?(我希望这不是我的电脑本身的问题)。编辑:从逻辑上讲,字段之间不需要填充,d
并且f
我还运行了以下代码以确保。
fmt.Println(unsafe.Offsetof(y.a))
fmt.Println(unsafe.Offsetof(y.b))
fmt.Println(unsafe.Offsetof(y.e))
fmt.Println(unsafe.Offsetof(y.d))
fmt.Println(unsafe.Offsetof(y.f))
fmt.Println(unsafe.Offsetof(y.c))
结果:
0
16
17
20
24
32
play.golang.org使用 32 位机器,所以我怀疑是否可以在那里复制!
解决方案
您计算的 48 字节对于 amd64 是正确的。
package main
import (
"fmt"
"unsafe"
)
type S2 struct { // align 16
a string // size 16 = 8 + 8
b bool // size 1
e bool // size 1
// pad size 2
d int32 // size 4
f bool // size 1
// pad size 7
c string // size 16 = 8 + 8
}
func main() {
y := S2{}
fmt.Println(unsafe.Sizeof(y))
fmt.Println(unsafe.Offsetof(y.a))
fmt.Println(unsafe.Offsetof(y.b))
fmt.Println(unsafe.Offsetof(y.e))
fmt.Println(unsafe.Offsetof(y.d))
fmt.Println(unsafe.Offsetof(y.f))
fmt.Println(unsafe.Offsetof(y.c))
fmt.Println(&y.a)
fmt.Println(&y.b)
fmt.Println(&y.e)
fmt.Println(&y.d)
fmt.Println(&y.f)
fmt.Println(&y.c)
}
输出:
48
0
16
17
20
24
32
0xc000070150
0xc000070160
0xc000070161
0xc000070164
0xc000070168
0xc000070170
推荐阅读
- google-analytics - 访问报告 API 的 Google 身份验证要求
- dynamics-crm - $batch 请求 - 与逐个执行的请求相比,它们是否提供客户端性能加速
- node.js - Firebase 生成圆形缩略图失败,代码为 1
- javascript - Jquery.Get 调用控制器方法并不总是有效
- algorithm - 魔方加密
- api - 当 precipType 为“rain”时,DarkSky 时间机器(历史)数据是否应显示 PrecipAccumulation
- postgresql - 我已经在 ubuntu 16.04 中安装了 Postgres 服务器 10.7,但我没有得到相同版本的 Postgres 客户端
- azure - 使用 Blob 存储触发器在 Azure 逻辑应用中禁用拆分功能时为空正文
- sql-server - 内存不足,无法完成此操作。请稍后再试,当excel中可能出现更多可用内存错误时
- python-3.x - 函数应该将数据存储到字典中