Featured image of post Go Slice切割边界问题

Go Slice切割边界问题

问题

如下代码

func Test(t *testing.T) {
PatchConvey("test", t, func () {
//your mock code...
PatchConvey("test case1", func () {
            var s []int
            
            s = append(s, 1, 2, 3)
            
            a := s[len(s):]
            b := s[len(s)]
            c := s[len(s)+1:]
            
            println(a)
            println(b)
            println(c)
        })
    })
}

有几个问题:

  1. a不会报错
  2. b会panic
  3. c会panic

原因

  1. b的[len(s)]肯定越界
  2. [:]切割Slice的方式是左闭右开的,
    • 冒号左边如果为空, 默认是0
    • 冒号右边如果为空, 默认是字符串len(s)
  3. a中冒号左边的是len(s), 没有超过右边默认的len(s), 所以不会panic, 这样切出来的就是一个空的slice
  4. c中的冒号左边len(s)+1, 超过了右边默认的len(s), 所以会panic

其他知识

  1. 如果slice有扩容操作, 那么就会使用新的内存; 如果没有扩容操作, 使用旧的内存
  2. append扩容的时候, slice的cap值会随着go的版本不同而略有不同(1.5版本下, s的cap为4; 1.6的版本下, s的cap为3)
Licensed under CC BY-NC-SA 4.0
Owner Rainbowly
Total [] user views [] site views [] page views
Built with Hugo
主题 StackJimmy 设计