1

我想提取字符串或文件标记之间的所有 html,我一直在使用 (perl) 模块 html::parser,我认为这将是一项简单的任务,但结果却非常棘手?我发现了一些有效但不知道如何将结果保存到字符串的代码?任何帮助表示赞赏,或者您是否可以向我展示一些有关如何使用 HTML::TokeParser 或类似方法实现此目的的代码。

谢谢

my $content=<<EOF;
<html xmlns="http://www.w3.org/1999/xhtml">
 <head>
   <title>Some title goes here</title>
 </head>
 <body bgcolor="#FFFFFF">
   <div id="leftcol">
     menu column
  </div>
  <div id="body">
   <p>some text goes here some text goes here<br />
    some text goes here some text goes here</p>
   <p><strong>some header</strong></p>
   <p>some text goes here some text goes here<br />
   some text goes here some text goes here</p>
    <p><img src="img.gif" /> image here</p>
   <p><strong>some header</strong></p>
   <p>some text goes here some text goes here<br />
   some text goes here some text goes here</p>
   </div>
    <div id="rightcol">
   news column
    </div>
 </body>
</html>
EOF


my $p = HTML::Parser->new( api_version => 3 );
$p->handler( start => \&start_handler, "self,tagname,attr" );
$p->parse($content);
exit;

sub start_handler {
    my $self = shift;
    my $tagname  = shift;
    my $attr = shift;
    my $text = shift;
    return unless ( $tagname eq 'body' );
    $self->handler( start => sub { print shift }, "text" );
    $self->handler( text =>  sub { print shift }, "text" );
    $self->handler( end  => sub {
    my ($endtagname, $self, $text) = @_;
         if($endtagname eq $tagname) {
         $self->eof;
         } else {
              print $text;
        }
    }, "tagname,self,text");
 }

如果我修改上面的子例程开始文本和结束处理程序,如下所示

为什么这些变量中的文本没有保存在我的文件中?

$self->handler( start => sub {  my ($text) = @_; $inner_body = $inner_body. $text; }, "text" );
$self->handler( text =>  sub {  my ($text) = @_; $inner_body = $inner_body. $text; }, "text" );
$self->handler( end  => sub {
       my ($endtagname, $self, $text) = @_;
       if($endtagname eq $tagname) {
            $self->eof;
           } else {
             $inner_body = $inner_body. $text;
           }
        }, "tagname,self,text");

}

打印 $inner_body; # <-- 打印空白 ???

期望的输出保存在变量中


   <div id="leftcol">
     menu column
  </div>
  <div id="body">
   <p>some text goes here some text goes here<br />
    some text goes here some text goes here</p>
   <p><strong>some header</strong></p>
   <p>some text goes here some text goes here<br />
   some text goes here some text goes here</p>
    <p><img src="img.gif" /> image here</p>
   <p><strong>some header</strong></p>
   <p>some text goes here some text goes here<br />
   some text goes here some text goes here</p>
   </div>
    <div id="rightcol">
   news column
    </div>
4

1 回答 1

1

你所要做的就是更换

print ...;

$inner_body .= ...;

就个人而言,我会改用 XML::LibXML。它可以处理 HTML 和 XML(通过使用解析器的适当方法)。您所拥有的是 XHTML(与 XML 兼容),因此我们parse_string使用parse_html_string.

use XML::LibXML               qw( );
use XML::LibXML::XPathContext qw( );

my $xpc = XML::LibXML::XPathContext->new();
$xpc->registerNs(h => 'http://www.w3.org/1999/xhtml');

my $parser = XML::LibXML->new();
my $doc = $parser->parse_string($content);
my ($body_node) = $xpc->findnodes('/h:html/h:body', $doc)
   or die;

my $inner_body = join '', map $_->toString(), $body_node->childNodes();
print $inner_body;
于 2013-05-28T18:23:10.580 回答