Golang—内存对齐

Golang是一种C家族的语言,关于内存对齐和C有大部分相通的地方。如果之前就对内存对齐有了解的话,很容易理解。

 先看一个例子吧

package main

import (
	"fmt"
	"unsafe"
)

type part struct {
	a bool
	b int32
	c int8
	d int64
	e byte
}

func main() {
	part1 := part{}
	fmt.Printf("bool size: %d, align: %d, offset: %d\n", unsafe.Sizeof(part1.a), unsafe.Alignof(part1.a), unsafe.Offsetof(part1.a))
	fmt.Printf("int32 size: %d, align: %d, offset: %d\n", unsafe.Sizeof(part1.b), unsafe.Alignof(part1.b), unsafe.Offsetof(part1.b))
	fmt.Printf("int8 size: %d, align: %d, offset: %d\n", unsafe.Sizeof(part1.c), unsafe.Alignof(part1.c), unsafe.Offsetof(part1.c))
	fmt.Printf("int64 size: %d, align: %d, offset: %d\n", unsafe.Sizeof(part1.d), unsafe.Alignof(part1.d), unsafe.Offsetof(part1.d))
	fmt.Printf("byte size: %d, align: %d, offset: %d\n", unsafe.Sizeof(part1.e), unsafe.Alignof(part1.e), unsafe.Offsetof(part1.e))
	fmt.Printf("part1 size: %d, align: %d\n", unsafe.Sizeof(part1), unsafe.Alignof(part1))
}

由结果可以看到bool int8 int32 int64 byte的大小,但是相加的结果并不是part结构体的结果,从结果可以看出来,bool占用了一个字节后,下一个int32类型占用4字节时是有4个字节偏移的,所以一共占用了八个字节,向后推导发现有些类型占用了比类型本身字节更大的空间。导致这个问题的原因就是内存对齐。

1. 为什么会有内存对齐这回事

大部分资料都在说两个原因

  1. 平台问题:并不是所有的硬件平台都能访问任意地址上的任意数据。
  2. 性能问题:访问未对齐内存需要cpu进行两次访问,对齐后只需要一次。

2. 内存对齐原则

  1. 对齐值为系统默认对齐值和类型大小长度的最小值
  2. 结构体内部字段对齐值为默认对齐值和字段最大类型长度的最小值。

 3. 内存对齐的使用

由于内存对齐的存在,使得类型按照不同的顺序排列属性可能会得到不同的大小,所以在受限条件下设计类型时需要注意。

package main

import (
	"fmt"
	"unsafe"
)

type part1 struct {
	a bool
	b int32
	c int8
	d int64
	e byte
}
type part2 struct {
	a bool
	e byte
	c int8
	b int32
	d int64
}

func main() {
	p1 := part1{}
	p2 := part2{}
	fmt.Printf("part1 size: %d\n", unsafe.Sizeof(p1))
	fmt.Printf("part2 size: %d\n", unsafe.Sizeof(p2))
}

从结果可以看到,顺序不用对类型体积还是有影响的。下面是对类型内存占用的示意图,-表示占空。

p1 : |a---|bbbb|c---|----|dddd|dddd|e---|----|

p2 : |aec-|bbbb|dddd|dddd|

从上面的示意可以看出part1和part2的占用方式,p2相比p1减少了一半属性占用空间。

 

参考材料:

1. https://go101.org/article/memory-layout.html

2. https://blog.csdn.net/u011957758/article/details/85059117

3. https://studygolang.com/articles/15540?fr=sidebar


 记录每天解决的小问题,积累起来去解决大问题。 

展开阅读全文

没有更多推荐了,返回首页