golang中的slice切片底层模型reflect.SliceHeader

slice 的底层模型为reflect.SliceHeader

// SliceHeader is the runtime representation of a slice.
// It cannot be used safely or portably and its representation may
// change in a later release.
// Moreover, the Data field is not sufficient to guarantee the data
// it references will not be garbage collected, so programs must keep
// a separate, correctly typed pointer to the underlying data.
type SliceHeader struct {
	Data uintptr // 对于的底层数组的地址的整型化表示
	Len  int
	Cap  int
}

我们可以使用unsafe.Pointer来查看

s := []byte{'h', 'e', 'l', 'l', 'o', ' ', 'w', 'o', 'r', 'l', 'd'}

sh := (*reflect.SliceHeader)(unsafe.Pointer(&s))
fmt.Printf("s : %#v\n", sh) // s : &reflect.SliceHeader{Data:0xc00000a0d0, Len:11, Cap:11}

// 截取切片
s1 := s[:5]
sh1 := (*reflect.SliceHeader)(unsafe.Pointer(&s1))
fmt.Printf("s1: %#v\n", sh1) // s1: &reflect.SliceHeader{Data:0xc00000a0d0, Len:5, Cap:11}

// append 没有超出范围,底层数组不变
s1 = append(s1, 'T')
sh1 = (*reflect.SliceHeader)(unsafe.Pointer(&s1))
fmt.Printf("s1: %#v\n", sh1) // s1: &reflect.SliceHeader{Data:0xc00000a0d0, Len:6, Cap:11}

// append超出了范围,底层数组的地址改变了
s2 := append(s, 'M')
sh2 := (*reflect.SliceHeader)(unsafe.Pointer(&s2))
fmt.Printf("s2: %#v\n", sh2) // s2: &reflect.SliceHeader{Data:0xc000014168, Len:12, Cap:24}

sh1 = (*reflect.SliceHeader)(unsafe.Pointer(&s1))
fmt.Printf("s1: %#v\n", sh1) // s1: &reflect.SliceHeader{Data:0xc00000a0d0, Len:6, Cap:11}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值