WWW ::机械化:: Firefox的循环虽然链接
我通过链接使用foreach
循环。我需要$mech->back();
来继续循环还是隐式的。WWW ::机械化:: Firefox的循环虽然链接
此外,我需要一个单独的$mech2
对象为每个循环嵌套?
我现在的代码被卡住了(它没有完成),并在没有找到td#tabcolor3
的第一页结束。
foreach my $sector ($mech->selector('a.link2'))
{
$mech->follow_link($sector);
foreach my $place ($mech->selector('td#tabcolor3'))
{
if (($mech->selector('td#tabcolor3', all=>1)) >= 1)
{
$mech->follow_link($place);
print $_->{innerHTML}, '\n'
for $mech->selector('td.dataCell');
$mech->back();
}
else
{
$mech->back();
}
}
不能从页面访问信息,当它不再显示。然而,这样foreach
作品是建立列表第一它是通过迭代之前,所以你写的代码应该罚款。
由于链接是绝对的,因此不需要拨打back
。如果您用过click
那么就必须在页面点击一个链接,但与follow_link
所有你正在做的是去一个新的URL。
也不需要检查要遵循的链接数,因为for
循环遍历空列表将不会被执行。
为了使事情更清晰,我建议您在循环之前将selector
的结果赋值给一个数组。
像这样
my @sectors = $mech->selector('a.link2');
for my $sector (@sectors) {
$mech->follow_link($sector);
my @places = $mech->selector('td#tabcolor3');
for my $place (@places) {
$mech->follow_link($place);
print $_->{innerHTML}, '\n' for $mech->selector('td.dataCell');
}
}
更新
我的道歉。看来,follow_link
是挑剔的,需要按照当前页面上的链接。
我建议您从每个链接中提取href
属性,并使用get
而不是follow_link
。
my @selectors = map $_->{href}, $mech->selector('a.link2');
for my $selector (@selectors) {
$mech->get($selector);
my @places = map $_->{href}, $mech->selector('td#tabcolor3');
for my $place (@places) {
$mech->get($place);
print $_->{innerHTML}, '\n' for $mech->selector('td.dataCell');
}
}
请让我知道这是否适用于您要连接到的网站。
我建议使用单独的$机甲的对象是:
foreach my $sector ($mech->selector('a.link2'))
{
my $mech = $mech->clone();
$mech->follow_link($sector);
foreach my $place ($mech->selector('td#tabcolor3'))
{
if (($mech->selector('td#tabcolor3', all=>1)) >= 1)
{
my $mech = $mech->clone();
$mech->follow_link($place);
print $_->{innerHTML}, '\n'
for $mech->selector('td.dataCell');
#$mech->back();
}
# else
# {
# $mech->back();
# }
}
我使用WWW:机械化:: Firefox来遍历使用Javascript的负荷一堆网址。页面不立即渲染,因此需要测试一个特定的页面元素是否可见(类似于Mechanize :: Firefox文档中的建议,除了测试中的两个xpaths),然后再决定下一个操作。
页面最终呈现一个XPath来“无信息”或某些约2-3秒后想要的东西。如果没有信息,我们会转到下一个网址。我认为存在某种竞争条件,这两种xpath不会立即导致间歇性地(在循环中的sleep 1
足够奇怪)造成MozRepl::RemoteObject: TypeError: can't access dead object
错误。
我的解决方案,似乎工作/提高可靠性是包围所有$mech->get
和$mech->is_visible
在eval{};
这样的:
eval{
$mech->get("$url");
$retries = 15; #test to see if element visible = page complete
while ($retries-- and ! $mech->is_visible(xpath => $xpath_btn) and ! $mech->is_visible(xpath => $xpath_no_info)){
sleep 1;
};
last if($mech->is_visible(xpath => $xpath_no_info)); #skip rest if no info page
};
其他人可能会认为这一改进。
感谢更多优雅的解决方案。我得到一个Mozrepl :: RemoteObject:TypeError - 不能访问这个行的死对象:= $ mech-> follow_link($ share); #it显示在上面...我认为有一个嵌套的问题...我是否需要一个单独的机甲物体作为以前的答案建议? – surfer190 2013-03-11 11:43:08
对不起,行是:$ mech-> follow_link($ place); – surfer190 2013-03-11 12:07:56
从[*最新的修改列表*](http://cpansearch.perl.org/src/CORION/WWW-Mechanize-Firefox-0.70/Changes),它看起来像从Firefox 15开始的“死对象”问题。已经更新了我的解决方案以展示另一种方法。 – Borodin 2013-03-11 12:51:50