赞
踩
切片是一种比较特殊的数据结构。它围绕动态数组的概念构建,可以按需自动增长和缩小。总的来说它可理解为动态数组,并根据切片里的元素自动调整切片长度。
常用定义方式如下
- var name []*type //定义方式一
- name := []*type{} //定义方式二
需要注意的是,切片指针只能存放内存地址的数据格式,需要获取对应数值时需要加上取值操作符“*”。例子如下
- package main
-
- import "fmt"
-
- func main() {
- var nums []*int
- for i := 0; i < 5; i++ {
- nums = append(nums, &i)
- }
- for i, v := range nums {
- _ = i
- fmt.Printf("%v ", v)
- }
- }
得到的结果为地址
0xc00001a0a8 0xc00001a0a8 0xc00001a0a8 0xc00001a0a8 0xc00001a0a8
打印输出时,加上取值操作符后,结果为
5 5 5 5 5
当然你可能已经发现了,加上取值操作符后我们预期出现的结果应该是:”0,1,2,3,4“,为什么会是“5,5,5,5,5“呢?
再看看地址,发现这五个数都是同一个内存地址。这说明在向nums中添加元素时我们添加的都是同一个内存地址。再往前推就是说明变量i的地址不变,只有值变了。
我们再仔细观察第一个循环,发现每次往nums里添加的是变量i的值,变量i在这个循环中地址始终不变。而由于nums作为切片指针,它只能存放地址,而这些地址又来自同一个变量,那么最后的结果肯定是相同的了。
解决办法也很简单,循环内重新定义一个中间变量,这样在每次循环这个变量的地址都会改变
- package main
-
- import "fmt"
-
- func main() {
- var nums []*int
- for i := 0; i < 5; i++ {
- var tmp int = i
- nums = append(nums, &tmp)
- }
- for _, v := range nums {
- fmt.Printf("%v ", *v)
- }
- }
结果为
0 1 2 3 4
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。