Golang understands slice features - capacity pointer expansion

Directly upload a piece of code to check your rank
        1. If your expected result is consistent with the result after running, congratulations, you have completely got slice

                2. If you understand the running results, it means that you understand the concept of slice, but you are not familiar with it and lack of practice

                3. If you can't understand the running results, then listen to my analysis carefully

func test_slice(){
   arr :=[...]int{0,1,2,3,4,5,6,7} 
   // cap=8-6
   var slice []int = arr[6:8:8]
   // 请思考实际容量
   fmt.Println(arr,slice,cap(slice))
   slice[1]=50
   //新slice2还与slice指向同一个数组吗
   var slice2 []int = append(slice, 100)
   //新slice3还与slice2指向同一个数组吗
   var slice3 []int = append(slice2, 200)
   //新slice4还与slice3指向同一个数组吗
   var slice4 []int = append(slice3, 300)
   slice3[1]=52
   slice4[1]=20
   fmt.Println("arr=",arr,"slice=",slice,"slice2=",slice2,"slice3=",slice3,"slice4=",slice4)
fmt.Println("内存地址:arr[1]=",&arr[7],"slice=",&slice[1],"slice2=",&slice2[1],"slice3=",&slice3[1],"slice4=",&slice4[1])
}

operation result

[0 1 2 3 4 5 6 7] [6 7] 2
arr= [0 1 2 3 4 5 6 50] slice= [6 50] slice2= [6 52 100] slice3= [6 52 100 200] slice4= [6 20 100 200 300]
内存地址:arr[1]= 0xc000092038 slice= 0xc000092038 slice2= 0xc00008e048 slice3= 0xc00008e048 slice4= 0xc000092088

analyze

     1. For the basic concept of slice, please refer to the official document. slice is a reference type, born for dynamic expansion of arrays. The bottom layer of the slice is a pointer reference to an array. If you change the slice, you are actually changing the value of the array pointed to by the slice

      2. If the slice directly points to an existing array, the capacity cannot exceed the subsequent length of the index of the array you point to, so the setting cannot exceed 8 (len(arr)), and the actual capacity of the slice is 2

      3. Every time a slice is appended, a value will be added to the end of the original slice, and a new slice will be generated (the slice address is different)

       4. The expansion of the slice is a 2-fold expansion. Each expansion generates a new array and copies the original value. Note that the append operation that does not exceed the capacity will not change the array pointed to by the slice, otherwise it will expand and point to a new array

        5. Based on the description in point 4, slice2 no longer points to the same array as slice, because the capacity exceeds 2, and slice2 is already expanded by 2*2=4

        6. Because slice2 already has cap=4, slice3 is still within the capacity, so slice3 and slice2 still point to the same expanded array, so change slice3[1] =52, slice2[1] will also change accordingly

        7. At the time of slice3, cap=4 has been used up. At this time, the append operation will be performed again, and the capacity will be expanded again at this time, 4*2=8, so slice4 points to the new array, so change slice4[1]=20, which is already the same as The previous slice is irrelevant

To sum up

        Reflects slice cap capacity knowledge, pointing characteristics, expansion mechanism, and changes after expansion

        If you don't understand, then you must carefully read the knowledge points of array and slice. After you understand it, do the exercises I posted. you'll get it right

Guess you like

Origin blog.csdn.net/m0_37298500/article/details/121991153