扩容机制

扩容时机:发生在slice append时,当slice的cap不足以容纳新元素,就会进行扩容

append() 底层逻辑

  1. 计算追加后slice的总长度n
  2. 如果总长度n大于原cap,则调用growslice计算容量大小,并申请内存(cap最小为n,具体扩容规则见growslice)
  3. 对扩容后的slice进行切片,长度为n,获取slice s,用以存储所有的数据
  4. 根据不同的数据类型,调用对应的复制方法,将原slice及追加的slice的数据复制到新的slice

growslice 计算容量大小的逻辑

  1. 如果新申请容量比2倍原有容量大,扩容大小为新申请容量
  2. 如果原slice长度小于1024,则扩容为原来2倍
  3. 否则在原slice长度大于等于1024,每次扩容为原来1.25倍
package main

import "fmt"

func main() {
	s1 := []int{}
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 1)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 2)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 3)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 4)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 5)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 6)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 7)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 8)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))
	s1 = append(s1, 9)
	fmt.Printf("len=%d,cap=%d\n", len(s1), cap(s1))

}
/*
len=0,cap=0
len=1,cap=1
len=2,cap=2 
len=3,cap=4 
len=4,cap=4 
len=5,cap=8 
len=6,cap=8 
len=7,cap=8 
len=8,cap=8 
len=9,cap=16
*/