Передать переменную в функцию обратного вызова - PullRequest
0 голосов
/ 17 октября 2019

Способ передачи переменной selector в функцию обратного вызова?

for _, selector := range listSelector {
    c.OnHTML(selector, func(e *colly.HTMLElement) {
        fmt.Println(selector) // Similar outputs
    })
}

Ожидаемый результат - другой селектор для выхода. Спасибо.

1 Ответ

1 голос
/ 17 октября 2019

В зависимости от , когда выполняется обратный вызов, может потребоваться создать копию переменной итерации внутри блока и использовать ее в замыкании.

for _, selector := range listSelector {
    sel := selector // create a copy
    c.OnHTML(sel, func(e *colly.HTMLElement) {
        fmt.Println(sel) // Similar outputs
    })
}

Если обратный вызоввыполняется, и он выходит перед следующей итерацией в цикле, вам не нужно этого делать, однако, если обратный вызов выполняется некоторое время спустя, вам необходимо передать копию переменной итерации в замыкание. Это связано с тем, что переменная итерации повторно используется для хранения значений повторения, что означает, что значение переменной из текущей итерации будет перезаписано значением из следующей итерации.

From spec :

Переменные итерации могут быть объявлены предложением «range» с использованием формы краткого объявления переменных (: =). В этом случае их типам присваиваются типы соответствующих значений итерации, а их область действия является блоком оператора for; они повторно используются в каждой итерации . Если переменные итерации объявлены вне оператора for, после выполнения их значения будут такими же, как в последней итерации.


Если вам интересно, это лучше объяснить в *Документация по каналам 1021 * Effective Go .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...