英文:
Passing a slice into a channel
问题
我正在尝试将切片的处理结果传递到一个通道中。以下是明显有问题的版本。我尝试了几种方法,但似乎都不太有效。我正在寻找一种惯用的方法来解决这个问题。
func gen() <-chan []int {
c := make(chan []int)
go func(c chan []int) {
defer close(c)
s := []int{0, 1, 2, 3}
for i := 0; i < len(s); i++ {
s[i] = -1
c <- s
}
}(c)
return c
}
func main() {
for s := range gen() {
fmt.Println(s)
}
}
结果:
[-1 -1 2 3]
[-1 -1 2 3]
[-1 -1 -1 -1]
[-1 -1 -1 -1]
英文:
I'm trying to pass the results of munging a slice into a channel. Here's the obviously broken version. I've tried a few ways of doing it that don't seem to work well. I'm looking for an idiomatic way of tackling this.
func gen() <-chan []int {
c := make(chan []int)
go func(c chan []int) {
defer close(c)
s := []int{0, 1, 2, 3}
for i := 0; i < len(s); i++ {
s[i] = -1
c <- s
}
}(c)
return c
}
func main() {
for s := range gen() {
fmt.Println(s)
}
}
Result:
[-1 -1 2 3]
[-1 -1 2 3]
[-1 -1 -1 -1]
[-1 -1 -1 -1]
答案1
得分: 15
这段代码不起作用,因为底层数组是相同的。所以你修改的是同一块内存。
这里有一个可行的示例。在每一轮中复制内存。
package main
import "fmt"
func gen() <-chan []int {
c := make(chan []int)
go func(c chan []int) {
defer close(c)
s := []int{0, 1, 2, 3}
for i := 0; i < len(s); i++ {
s[i] = -1
newSlice := make([]int, len(s))
copy(newSlice, s)
c <- newSlice
}
}(c)
return c
}
func main() {
for s := range gen() {
fmt.Println(s)
}
}
输出结果:
[-1 1 2 3]
[-1 -1 2 3]
[-1 -1 -1 3]
[-1 -1 -1 -1]
英文:
It does not work because the underlying array is the same. So you are modifying the same memory.
Here is a working example. Copy the memory at each round.
http://play.golang.org/p/OXfKVg8ZlZ
package main
import "fmt"
func gen() <-chan []int {
c := make(chan []int)
go func(c chan []int) {
defer close(c)
s := []int{0, 1, 2, 3}
for i := 0; i < len(s); i++ {
s[i] = -1
newSlice := make([]int, len(s))
copy(newSlice, s)
c <- newSlice
}
}(c)
return c
}
func main() {
for s := range gen() {
fmt.Println(s)
}
}
Output
[-1 1 2 3]
[-1 -1 2 3]
[-1 -1 -1 3]
[-1 -1 -1 -1]
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论