是将selector
变量传递给回调函数的方法吗?
for _, selector := range listSelector {
c.OnHTML(selector, func(e *colly.HTMLElement) {
fmt.Println(selector) // Similar outputs
})
}
预期结果是输出的不同选择器。 谢谢。
答案 0 :(得分:1)
取决于何时执行回调,您可能需要在块内创建迭代变量的副本,并在闭包中使用它。
for _, selector := range listSelector {
sel := selector // create a copy
c.OnHTML(sel, func(e *colly.HTMLElement) {
fmt.Println(sel) // Similar outputs
})
}
如果执行了回调并且在循环中的下一次迭代之前退出,则无需执行此操作,但是,如果在某个时间之后执行回调,则需要将迭代变量的副本传递给闭包。这是因为重用迭代变量来保存迭代值,这意味着当前迭代中的变量值将被下一次迭代中的值覆盖。
来自spec:
可以通过“ range”子句使用 短变量声明(:=)的形式。在这种情况下,它们的类型是 设置为各个迭代值的类型,其范围为 “ for”语句的框; 它们在每次迭代中都会重复使用。 如果迭代变量在“ for”语句之外声明, 执行后,它们的值将是最后一次迭代的值。
如果您有兴趣,可以在Effective Go关于渠道的文档中对此进行更好的解释。