我正在尝试通过网站进行分页,为了请求下一页,需要当前页面上的信息。
function paginateSite(numPages, cb) {
var stringToGetToNextPage = ''
for (var i = 0; i < numPages; i++) {
(function(i, stringToGetToNextPage) {
request({
url: 'http://website.com',
qs: {
nextPage: stringToGetToNextPage
}
},
function(err, res, body) {
body_json = JSON.parse(body)
console.log(body_json.stringToGetToNextPage)
})
})(i, stringToGetToNextPage)
}
}
正如您所看到的,我无法在匿名函数之外设置stringToGetToNextPage。我查看了异步库文档,但无法找到解决我问题的任何内容。
有人遇到过这个问题吗?这似乎是异步范式没有一个干净的解决方案。
编辑:问题#2,可以想象一种没有递归的方法吗?递归适用于小例子,但现在我有一个stackoverflow案例,可以在没有警告的情况下终止程序(并占用内存)。
答案 0 :(得分:1)
递归就是这样做的方法。
首先,将一个函数分解出来以检索单个页面:
function requestPage(stringToGetToNextPage, callback) {
request({
url: 'http://website.com',
qs: {
nextPage: stringToGetToNextPage
}
}, function(err, res, body) {
if (err) { callback(err); }
else { callback(null, JSON.parse(body)); }
});
}
然后,创建一个可以递归调用自身以获取每个连续页面的函数:
function requestAllPages(stringToGetToNextPage, callback) {
requestPage(stringToGetToNextPage, function (err, page) {
if (err) { callback(err); }
else if (page && page.stringToGetToNextPage) {
requestAllPages(page.stringToGetToNextPage, callback);
}
else { callback(); }
});
}
然后全力以赴:
requestAllPages(null, function () {
console.log('Done!');
});
修改如果您确实想要对特定数量的网页进行分页而不是结束,只需对requestAllPages
进行少量修改就可以实现这一目标:
function requestPages(numPages, stringToGetToNextPage, callback) {
if (numPages <= 0) { callback(); return; }
requestPage(stringToGetToNextPage, function (err, page) {
if (err) { callback(err); }
else if (page && page.stringToGetToNextPage) {
requestPages(numPages - 1, page.stringToGetToNextPage, callback);
}
else { callback(); }
});
}
requestPages(20, null, function () {
console.log('Done!');
});
答案 1 :(得分:1)
写一个递归函数。
function get_page(next_page_number, last_page_number, string_needed, callback) {
request(
{
url: 'http://website.com',
qs: {
nextPage: string_needed
}
},
function(err, res, body) {
// NB: Bad variable name. `body` is JSON. `body_json` won't be.
var body_json = JSON.parse(body);
if (next_page_number == last_page_number) {
callback(body_json);
} else {
get_page(
next_page_number + 1,
last_page_number,
body_json.stringToGetToNextPage,
callback
);
}
}
);
}
get_page(1, 27, "", function (body_json) { console.log(body_json); });