Go语言中,slice作为函数参数时是值拷贝,意味着函数将获得切片的副本:指向基础数组的起始地址的指针,以及切片的长度和容量。
func main() {
nums:=make([]int,0,100)
fmt.Printf("main里面的地址:%p\n",&nums)
try(nums)
}
func try(nums []int) {
fmt.Printf("try里面的地址:%p\n",&nums)
}
输出结果:
可以看出两个nums切片的地址不一样,从而知道是只拷贝。
当不对切片进行增加和删除时,可以通过对调用函数中的切片的进行修改,然后副本会传给原来的函数。
func main() {
nums:=[]int{1,2,3,4}
try(nums)
fmt.Println("main中的nums",nums)
}
func try(nums []int) {
nums[1] = 4
fmt.Println("try函数里面的nums",nums)
}
输出结果:
从输出结果可以看出,try函数对切片的修改,main函数里面出现了改变。
如果对通过函数参数对切片进行增加和删除,就达不到想要的结果。因为增加和删除需要对slice的长度做出修改,值拷贝就行不通了,就需要串slice本身内存的地址。
func main() {
nums:=[]int{1,2,3,4}
try(nums)
fmt.Println("main中的nums",nums)
}
func try(nums []int) {
nums = append(nums,100)
fmt.Println("try函数里面的nums",nums)
}
输出结果:
有输出结果可以看出main函数没有切片修改。
如果想要用函数传参对切片做出修改,那么就需要用到指针。
func main() {
nums:=[]int{1,2,3,4}
try(&nums)
fmt.Println("main中的nums",nums)
}
func try(nums *[]int) {
*nums = append(*nums,100)
fmt.Println("try函数里面的nums",*nums)
}
输出结果: