看一看“
有效执行”的“并行化”部分,可以找到解决方案的想法。本质上,您必须在函数的每个返回路径上关闭通道。实际上,这是defer语句的一个很好的用例:
func Crawl(url string, depth int, fetcher Fetcher, ret chan string) { defer close(ret) if depth <= 0 { return } body, urls, err := fetcher.Fetch(url) if err != nil { ret <- err.Error() return } ret <- fmt.Sprintf("found: %s %q", url, body) result := make([]chan string, len(urls)) for i, u := range urls { result[i] = make(chan string) go Crawl(u, depth-1, fetcher, result[i]) } for i := range result { for s := range result[i] { ret <- s } } return}func main() { result := make(chan string) go Crawl("http://golang.org/", 4, fetcher, result) for s := range result { fmt.Println(s) }}您的代码的本质区别在于,每个Crawl实例都有其自己的返回通道,而调用程序函数则在其返回通道中收集结果。



