比如 slice 的 append,按我的理解:
1,扩容就生成新的底层数组,修改新的 slice 不会影响原来底层数组;
2,不扩容就不会生成新的数组,修改新的 slice 会修改原来的底层数组;
觉得这种问题很容易掉坑,求教有什么好习惯可以避免掉坑。
1
dongisking 2018-11-07 13:37:28 +08:00
另外一个坑
|
2
cheshire 2018-11-07 13:37:30 +08:00 via Android
初始化的时候能知道大小最好,不然的话指定一个比较大的 capacity
|
3
goofool OP @dongisking 这个结果是唯一的吧,会有第二种情况吗
|
5
brucewuio 2018-11-07 14:10:36 +08:00
其实《 The Go Programming Language 》 说的挺清楚的 上面也说尽量用数组的抽象 slice 很少直接用数组 加操作直接 append 减操作就[x:y] 截取
|
6
anonymous256 2018-11-07 14:13:21 +08:00
这里有个不错的坑,参见: https://www.golangtc.com/t/5565344ab09ecc3d42000026
```golang var dynaArr []string dynaArr = append(dynaArr, "one") dynaArr = append(dynaArr, "two") dynaArr = append(dynaArr, "three") fmt.Println(dynaArr) ``` 这样写就好 |
7
sirgod 2018-11-07 14:21:02 +08:00
多踩几次坑就好了
|
8
zhujinliang 2018-11-07 14:21:32 +08:00
@goofool 通常情况下接收方都是作为消费者,只需读取数据,不需修改数据
如果函数不返回数组切片,就不要修改其内容 如果调用函数是为了获得一个数组的返回,那让函数自行 make,然后返回数组: func getSlice() []int { s := make([]int, ...) // 在这个函数内部创建 /// return s } outS := getSlice() 如果函数既需要读取数组里的内容,又需要修改这个数组里的数据或追加数据,让函数接收一个数组同时返回一个数组 func modifySlice(s []int) []int { s = append(s, ...) return s } outS = modifySlice(outS) |
10
goofool OP |
11
madiks 2018-11-07 14:33:38 +08:00 1
slice 本身是一个结构体,里面有三个字段:当前 slice 第一个元素在底层数组的指针、slice 长度和 slice 容量。创建 slice 就是基于底层数组生成一个这样的结构体,append 的扩容就是新申请原底层数组一倍的内存,再把原底层数组的内容拷贝过来。大部分时候你不需要关心是否扩容,只要记住 slice 是指类型,作为参数传递会拷贝就行了
```golang type slice struct { array unsafe.Pointer len int cap int } ``` 推荐阅读: https://research.swtch.com/godata |
12
goofool OP 最近用 gopacket 这个包,里面有个类似的 Data()方法实现
https://gist.github.com/goofool/4f9e3514a65a97ffa9f0a5eb273fa1fb 结果: https://gist.github.com/goofool/1bfa9898dc6495c64d7120f970278db9 |
13
lrz0lrz 2018-11-07 16:33:39 +08:00
@dongisking #1 这个坑好像 JS 的
|
16
asAnotherJack 2018-11-07 17:39:48 +08:00
好巧,几十分钟前也刚看到这儿,看 reader 的 read 方法时想到的这个问题,马一下等 v 友的解答
|
17
tiedan 2018-11-07 19:31:11 +08:00
@dongisking 对切片进行切片操作产生的是新的切片,不会影响原来的切片
|
18
trait 2018-11-07 19:35:38 +08:00
如果这么容易引起无意操作,没有人提 issue 要求官方给个解决方案么
|
20
dongisking 2018-11-07 20:25:11 +08:00
@tiedan 原来是这样
|