【问题标题】:How to extract a column of a table from html page using perl modules?如何使用 perl 模块从 html 页面中提取表格的列?
【发布时间】:2012-12-20 22:26:39
【问题描述】:

我有以下网页部分的 html 代码。

<h2 id="failed_process">Failed Process</h2>
<table border="1">
  <thead>
    <tr>
      <th>
        <b>pid</b>
      </th>
      <th>
        <b>Priority</b>
      </th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td id="90"><a href="details.jsp?pid=p_201211162334&refresh=0">p_201211162334</a></td>
      <td id="priority_90">NORMAL</td>
    </tr>
    <tr>
      <td id="91"><a href="details.jsp?pid=p_201211163423&refresh=0">p_201211163423</a></td>
      <td id="priority_91">NORMAL</td>
    </tr>
    <tr>
      <td id="98"><a href="details.jsp?pid=p_201211166543&refresh=0">p_201211166543</a></td>
      <td id="priority_98">NORMAL</td>
    </tr>
  </tbody>
</table>
<hr>

我需要提取 pid 列。输出应该看起来像

pid
p_201211162334
p_201211163423
p_201211166543

“失败进程”表的表数为 4。但问题是,如果我提到表数为 4,并且网页中没有失败的任务,它将转到下一个表并获取 pid下一个表导致错误的 pid。

我正在使用下面的代码来获取结果。

#!/usr/bin/perl
 use strict; 
 use warnings;
 use lib qw(..);
 use HTML::TableExtract;

 my $content = get("URL");
 my $te = HTML::TableExtract->new(
 headers => [qw(pid)], attribs => { id => 'failed_process' },
 );

 $te->parse($content);

 foreach my $col ($te->rows) {
 print ("\t", @$col), "\n";
 }

但我收到以下错误:

Can't call method "rows" on an undefined value 

【问题讨论】:

  • id =&gt; 'failed_process'不是表的id,而是表头
  • 是的!我如何提取 pid 引用该标头的 id?
  • 可能你需要先获取表然后获取行?请查看使用模块的示例 - search.cpan.org/~msisk/HTML-TableExtract-2.11/lib/HTML/…
  • KostiaShiian :我多次查看上述链接。它没有所需的详细信息.. !!
  • 查看Mojo::UserAgent。使用这个模块可以很容易地完成。

标签: perl html-parsing perl-module


【解决方案1】:

使用我最喜欢的 DOM 解析器 Mojo::DOM 来自 Mojolicious suite,它看起来像这样:

#!/usr/bin/env perl

use strict;
use warnings;
use feature 'say';
use Mojo::DOM;

# instantiate with all DATA lines
my $dom = Mojo::DOM->new(do { local $/; <DATA> });

# extract all first column cells
$dom->find('table tr')->each(sub {
    my $cell = shift->children->[0];
    say $cell->all_text;
});

__DATA__
<h2 id="failed_process">Failed Process</h2>
<table border="1">
    ...

输出:

pid
p_201211162334
p_201211163423
p_201211166543

【讨论】:

    【解决方案2】:

    $te-&gt;parse($html) 之后你可以添加一些类似foreach my $table ($te-&gt;tables) .. 然后你可以得到行$table-&gt;rows。您也可以使用Data::Dumper 来分析$te

    【讨论】:

    • 嗯..我尝试了上述更改.. 它不起作用.. !!
    • 你分析过 Data::Dumper($te) 的输出吗?
    • 是的,我做到了.. 这是 o/p $VAR1 = bless( {'_ts_sequential' => [], 'headers' => ['pid' ], 'br_translate' => 1, 'gridmap' => 1, 'attribs' => { 'id' => 'failed_process' }, '_counts' => [ 5, 3 ], '_tablestack' => [] }, 'HTML::TableExtract' );
    • 此代码有效:使用严格;使用警告;使用 HTML::TableExtract;使用 Data::Dumper;我的$内容;打开 (F,') { $content.= $_;我的 $te = HTML::TableExtract->new( headers => [qw(pid)] ); $te->解析($内容);我的@table = $te->tables; foreach my $row ($table[0]->rows) { print join(',', @$row), "\n"; }
    • 感谢石安!!但是当我直接将这段代码与 URL 一起使用时,它不起作用!!
    猜你喜欢
    • 2014-11-23
    • 1970-01-01
    • 1970-01-01
    • 2012-06-02
    • 2011-04-26
    • 1970-01-01
    • 1970-01-01
    • 2012-11-15
    • 2021-05-31
    相关资源
    最近更新 更多