我尝试使用这种模式的<input>类型隐藏的字段匹配︰

/<input type="hidden" name="([^"]*?)" value="([^"]*?)" />/

这是示例表单数据︰

<input type="hidden" name="SaveRequired" value="False" /><input type="hidden" name="__VIEWSTATE1" value="1H4sIAAtzrkX7QfL5VEGj6nGi+nP" /><input type="hidden" name="__VIEWSTATE2" value="0351118MK" /><input type="hidden" name="__VIEWSTATE3" value="ZVVV91yjY" /><input type="hidden" name="__VIEWSTATE0" value="3" /><input type="hidden" name="__VIEWSTATE" value="" /><input type="hidden" name="__VIEWSTATE" value="" />

但我不敢确定的typenamevalue的属性始终会以相同的顺序。如果最后出现的type属性,匹配将失败,因为我模式中它是在开始。

问题︰
如何更改我模式,因此它将匹配无论<input>标记中的属性的位置?

P.S. :顺便说一下我使用Adobe Air测试正则表达式基于正则表达式桌面工具

2010-11-20 05:33:32
问题评论:

正则表达式是绝好的解决方案如果您可以生成的 html 控制,因为它是 regual 与不定期的辩论,但我的情况我不知道 html 将如何更改在未来这样最好的事情是我而不是正则表达式使用分析器,i 在部分项目中使用正则表达式我正在拥有控制权

回答:

与所有答案此处,您尝试执行的正则表达式是非常有效的解决方案。这是因为您不尝试匹配平衡标记 — 要使用正则表达式是不可能的 !但只匹配中的一个标记,而这是完全正则。

这里不过是问题。不能您需要使用一个正则表达式...做个匹配捕获<input>标记,然后做进一步处理上的。请注意,这将仅当任何属性值中,有>字符,因此它并不完美,但它应该清醒输入足够了。

下面是一些 Perl (伪) 代码,以显示您明白我的意思︰

my $html = readLargeInputFile();

my @input_tags = $html =~ m/
    (
        <input                      # Starts with "<input"
        (?=[^>]*?type="hidden")     # Use lookahead to make sure that type="hidden"
        [^>]+                       # Grab the rest of the tag...
        />                         # ...except for the />, which is grabbed here
    )/xgm;

# Now each member of @input_tags is something like <input type="hidden" name="SaveRequired" value="False" />

foreach my $input_tag (@input_tags)
{
  my $hash_ref = {};
  # Now extract each of the fields one at a time.

  ($hash_ref->{"name"}) = $input_tag =~ /name="([^"]*)"/;
  ($hash_ref->{"value"}) = $input_tag =~ /value="([^"]*)"/;

  # Put $hash_ref in a list or something, or otherwise process it
}

基本的原则是,不要试图做太多使用一个正则表达式。您注意到,正则表达式强制使用一定数量的订单。因此需要做什么而是要首先匹配上下文要提取,然后 submatching 的数据吗。

编辑︰但是,我会同意,一般情况下,使用 HTML 分析器是可能更容易和更好,确实应该考虑重新设计您的代码或重新检查您的目标。:-)但我必须为与机械反应的分析 HTML 的任何子集是不可能发布此答案︰ HTML 和 XML 都不规则时认为整个规范,但标记的规范是 decently 正则,当然内 PCRE 的威力。

不与所有这里的答案。:)

@tchrist︰ 当我发布我此处没有您的答案。;-)

yah 嗯 — — 由于某种原因我花更长的时间比您键入。我认为我的键盘必须需要 greasing。:)

这就是无效的 HTML-它应该是值 ="& l t;是否真的确实就此? & gt;"如果他抓取操作位置资源表现不佳,转义等,随后他还需要更复杂的解决方案 — 但如果他们权限执行该操作 (如果他有对它的控制,他应该确保它是正确) 然后他没什么关系。

强制性链接到有关该主题的最佳等答案 (可能是最好这样回答段)︰ stackoverflow.com/questions/1732348/...

哦是,您可以利用 Regexes 分析 HTML !

您正在尝试的任务,是 regexes完全正常 !

真的大多数人低估与正则表达式解析 HTML 的难度,因此不当将这样做。

但这并不是一些相关的计算理论的根本缺陷。这里,很多 parroted,silliness,但您不相信它们。

所以,尽管它肯定可以完成 (此发布可作为现有的 incontrovertible 这一事实证明),这并不意味着它应该是。

您必须决定自己无论是到什么金额写入专用、 特殊用途的 HTML 解析器,从 regexes 的任务。大多数人不是。


常规的基于正则表达式的 HTML 分析解决方案

首先我将介绍用于分析任意HTML 与 regexes 是多么容易。在结束此过帐,但分析器的核心的完整程序是︰

for (;;) {
  given ($html) {
    last                    when (pos || 0) >= length;
    printf "@%d=",              (pos || 0);
    print  "doctype "   when / G (?&doctype)  $RX_SUBS  /xgc;
    print  "cdata "     when / G (?&cdata)    $RX_SUBS  /xgc;
    print  "xml "       when / G (?&xml)      $RX_SUBS  /xgc;
    print  "xhook "     when / G (?&xhook)    $RX_SUBS  /xgc;
    print  "script "    when / G (?&script)   $RX_SUBS  /xgc;
    print  "style "     when / G (?&style)    $RX_SUBS  /xgc;
    print  "comment "   when / G (?&comment)  $RX_SUBS  /xgc;
    print  "tag "       when / G (?&tag)      $RX_SUBS  /xgc;
    print  "untag "     when / G (?&untag)    $RX_SUBS  /xgc;
    print  "nasty "     when / G (?&nasty)    $RX_SUBS  /xgc;
    print  "text "      when / G (?&nontag)   $RX_SUBS  /xgc;
    default {
      die "UNCLASSIFIED: " .
        substr($_, pos || 0, (length > 65) ? 65 : length);
    }
  }
}

请参阅如何,是否易于阅读?

当写入,它标识每个段 HTML 并告诉找到那个。您可以轻松地修改它执行的操作与任何给定类型的棋子,或更具体的类型,而这些不需要的任何其他。

我有任何失败的测试用例 (左:)︰ 我已对 10 万多个 HTML 文件成功运行此代码 — 每一个我可以快速而轻松地让我的手。之外,我已经也在上运行该文件特别是构造破坏简单分析程序。

这是是天真分析器。

哦,我敢肯定它并非完美,但我还没有设法还中断了它。我图即使东西一样,此修复程序可以很容易地适应由于程序的清晰的结构。即使大量正则表达式的程序应具有结构。

现在,这就是视野,让我来解决操作问题。

解决使用 Regexes 操作任务的演示

包括下面的小html_input_rx程序产生下面的输出,以便您可以看到,使用 regexes 分析 HTML 顺利运行您要做的︰

% html_input_rx Amazon.com-_Online_Shopping_for_Electronics,_Apparel,_Computers,_Books,_DVDs_&_more.htm 
input tag #1 at character 9955:
       class => "searchSelect"
          id => "twotabsearchtextbox"
        name => "field-keywords"
        size => "50"
       style => "width:100%; background-color: #FFF;"
       title => "Search for"
        type => "text"
       value => ""

input tag #2 at character 10335:
         alt => "Go"
         src => "http://g-ecx.images-amazon.com/images/G/01/x-locale/common/transparent-pixel._V192234675_.gif"
        type => "image"

分析输入的标记信息,请参阅无恶意的输入

下面是程序生成上面的输出的源代码。

#!/usr/bin/env perl
#
# html_input_rx - pull out all <input> tags from (X)HTML src
#                  via simple regex processing
#
# Tom Christiansen <tchrist@perl.com>
# Sat Nov 20 10:17:31 MST 2010
#
################################################################

use 5.012;

use strict;
use autodie;
use warnings FATAL => "all";    
use subs qw{
    see_no_evil
    parse_input_tags
    input descape dequote
    load_patterns
};    
use open        ":std",
          IN => ":bytes",
         OUT => ":utf8";    
use Encode qw< encode decode >;

    ###########################################################

                        parse_input_tags 
                           see_no_evil 
                              input  

    ###########################################################

until eof(); sub parse_input_tags {
    my $_ = shift();
    our($Input_Tag_Rx, $Pull_Attr_Rx);
    my $count = 0;
    while (/$Input_Tag_Rx/pig) {
        my $input_tag = $+{TAG};
        my $place     = pos() - length ${^MATCH};
        printf "input tag #%d at character %d:
", ++$count, $place;
        my %attr = ();
        while ($input_tag =~ /$Pull_Attr_Rx/g) {
            my ($name, $value) = @+{ qw< NAME VALUE > };
            $value = dequote($value);
            if (exists $attr{$name}) {
                printf "Discarding dup attr value '%s' on %s attr
",
                    $attr{$name} // "<undef>", $name;
            } 
            $attr{$name} = $value;
        } 
        for my $name (sort keys %attr) {
            printf "  %10s => ", $name;
            my $value = descape $attr{$name};
            my  @Q; given ($value) {
                @Q = qw[  " "  ]  when !/'/ && !/"/;
                @Q = qw[  " "  ]  when  /'/ && !/"/;
                @Q = qw[  ' '  ]  when !/'/ &&  /"/;
                @Q = qw[ q( )  ]  when  /'/ &&  /"/;
                default { die "NOTREACHED" }
            } 
            say $Q[0], $value, $Q[1];
        } 
        print "
";
    } 

}

sub dequote {
    my $_ = $_[0];
    s{
        (?<quote>   ["']      )
        (?<BODY>    
          (?s: (?! k<quote> ) . ) * 
        )
        k<quote> 
    }{$+{BODY}}six;
    return $_;
} 

sub descape {
    my $string = $_[0];
    for my $_ ($string) {
        s{
            (?<! % )
            % ( p{Hex_Digit} {2} )
        }{
            chr hex $1;
        }gsex;
        s{
            & 43 
            ( [0-9]+ )
            (?: ; 
              | (?= [^0-9] )
            )
        }{
            chr     $1;
        }gsex;
        s{
            & 43 x
            ( p{ASCII_HexDigit} + )
            (?: ; 
              | (?= P{ASCII_HexDigit} )
            )
        }{
            chr hex $1;
        }gsex;

    }
    return $string;
} 

sub input { 
    our ($RX_SUBS, $Meta_Tag_Rx);
    my $_ = do { local $/; <> };  
    my $encoding = "iso-8859-1";  # web default; wish we had the HTTP headers :(
    while (/$Meta_Tag_Rx/gi) {
        my $meta = $+{META};
        next unless $meta =~ m{             $RX_SUBS
            (?= http-equiv ) 
            (?&name) 
            (?&equals) 
            (?= (?&quote)? content-type )
            (?&value)    
        }six;
        next unless $meta =~ m{             $RX_SUBS
            (?= content ) (?&name) 
                          (?&equals) 
            (?<CONTENT>   (?&value)    )
        }six;
        next unless $+{CONTENT} =~ m{       $RX_SUBS
            (?= charset ) (?&name) 
                          (?&equals) 
            (?<CHARSET>   (?&value)    )
        }six;
        if (lc $encoding ne lc $+{CHARSET}) {
            say "[RESETTING ENCODING $encoding => $+{CHARSET}]";
            $encoding = $+{CHARSET};
        }
    } 
    return decode($encoding, $_);
}

sub see_no_evil {
    my $_ = shift();

    s{ <!    DOCTYPE  .*?         > }{}sx; 
    s{ <! [ CDATA [ .*?    ]] > }{}gsx; 

    s{ <script> .*?  </script> }{}gsix; 
    s{ <!--     .*?        --> }{}gsx;

    return $_;
}

sub load_patterns { 

    our $RX_SUBS = qr{ (?(DEFINE)
        (?<nv_pair>         (?&name) (?&equals) (?&value)         ) 
        (?<name>             (?=  pL ) [w-] + (?<= pL )   )
        (?<equals>          (?&might_white)  = (?&might_white)    )
        (?<value>           (?&quoted_value) | (?&unquoted_value) )
        (?<unwhite_chunk>   (?: (?! > ) S ) +                    )
        (?<unquoted_value>  [w-] *                              )
        (?<might_white>     s *                                  )
        (?<quoted_value>
            (?<quote>   ["']      )
            (?: (?! k<quote> ) . ) *
            k<quote> 
        )
        (?<start_tag>  < (?&might_white) )
        (?<end_tag>          
            (?&might_white)
            (?: (?&html_end_tag) 
              | (?&xhtml_end_tag) 
             )
        )
        (?<html_end_tag>       >  )
        (?<xhtml_end_tag>    / >  )
    ) }six; 

    our $Meta_Tag_Rx = qr{                          $RX_SUBS 
        (?<META> 
            (?&start_tag) meta 
            (?:
                (?&might_white) (?&nv_pair) 
            ) +
            (?&end_tag)
        )
    }six;

    our $Pull_Attr_Rx = qr{                         $RX_SUBS
        (?<NAME>  (?&name)      )
                  (?&equals) 
        (?<VALUE> (?&value)     )
    }six;

    our $Input_Tag_Rx = qr{                         $RX_SUBS 

        (?<TAG> (?&input_tag) )

        (?(DEFINE)

            (?<input_tag>
                (?&start_tag)
                input
                (?&might_white) 
                (?&attributes) 
                (?&might_white) 
                (?&end_tag)
            )

            (?<attributes>
                (?: 
                    (?&might_white) 
                    (?&one_attribute) 
                ) *
            )

            (?<one_attribute>
                
                (?&legal_attribute)
                (?&might_white) = (?&might_white) 
                (?:
                    (?&quoted_value)
                  | (?&unquoted_value)
                )
            )

            (?<legal_attribute> 
                (?: (?&optional_attribute)
                  | (?&standard_attribute)
                  | (?&event_attribute)
            # for LEGAL parse only, comment out next line 
                  | (?&illegal_attribute)
                )
            )

            (?<illegal_attribute>  (?&name) )

            (?<required_attribute> (?#no required attributes) )

            (?<optional_attribute>
                (?&permitted_attribute)
              | (?&deprecated_attribute)
            )

            # NB: The white space in string literals 
            #     below DOES NOT COUNT!   It's just 
            #     there for legibility.

            (?<permitted_attribute>
                  accept
                | alt
                | bottom
                | check box
                | checked
                | disabled
                | file
                | hidden
                | image
                | max length
                | middle
                | name
                | password
                | radio
                | read only
                | reset
                | right
                | size
                | src
                | submit
                | text
                | top
                | type
                | value
            )

            (?<deprecated_attribute>
                  align
            )

            (?<standard_attribute>
                  access key
                | class
                | dir
                | ltr
                | id
                | lang
                | style
                | tab index
                | title
                | xml:lang
            )

            (?<event_attribute>
                  on blur
                | on change
                | on click
                | on dbl   click
                | on focus
                | on mouse down
                | on mouse move
                | on mouse out
                | on mouse over
                | on mouse up
                | on key   down
                | on key   press
                | on key   up
                | on select
            )
        )
    }six;

}

UNITCHECK {
    load_patterns();
} 

END {
    close(STDOUT) 
        || die "can't close stdout: $!";
} 

就可以了 !对其执行任何操作 !:)

只有可以判断您的技能与 regexes 是否由任何特定的分析任务。每个人的技能的级别是不同的并且每个新的任务不同。您有一组明确定义的输入作业,regexes 显然是 HTML 的正确的选择,因为它是 HTML 的一件小事,如果必须使用有限处理一部分共同制定一些。甚至正则表达式初学者应能处理与 regexes 的那些作业。任何其他操作是一种浪费。

但是,HTML 开始变得小于固定下,一旦它开始以 ramify 方式后无法预测,但一旦以匹配更多不同类型或使用更复杂的依赖关系的事情,哪些是完全合法的,将最终会到达一个点必须努力工作以一种解决方案,使用 regexes,您必须使用的分析类不会影响。其中,保本点降到取决于再次自己得心应手地使用 regexes。

那么怎么办?

我不会告诉您,您必须做什么或不执行哪些操作。我认为这是错误的。我只是想要向您展示 possibilties、 有点令您耳目一新。您可以选择您想要做和要做它的方式。有一些不是绝对 — — 并没有其他人知道自己的情况以及您自己做。如果事情看起来像是过多的工作,很好地,也许是。编程应该是有趣,您知道。如果不是这样,您可能会这样错误。

一个可以看我的html_input_rx程序在任意数量的有效方法。一个此类时,您实际上可以分析 HTML 与正则表达式。但另一种是很得多,得多得多,就越难比几乎任何人都曾认为它是。这很容易导致我的程序是什么应该证明结论做,是因为它真的很难。

我不会同意的。当然如果我在我的程序中所做的一切没有意义给您一些研究后,然后您应尝试 regexes 用于这种类型的任务。特定的 html,regexes 非常好,但一般的 html,它们于让疯狂的。使用分析类所有的时间,尤其是我还没有生成自己的 HTML。

Regexes 适合在小型HTML 分析问题,为大的 pessimal

即使我的程序不会执行的您为什么应该使用 regexes 分析常规 HTML 作为例证 — — 这没关系,因为我比较适用于该 ☺,才能 — — 它仍然应该是使更多的人将是特别常见的 eye-opener 和大的麻烦,编写不能读取、 非结构化的并且不可维护模式的危险习惯。

模式并不一定是丑陋的他们不一定要硬。如果您创建了丑陋的模式,则对您,不是它们的反射。

您 Exquisite 正则表达式语言

我已经被要求指出 Perl 中的写入我的 proferred 解决方案针对您的问题。是您对感到惊讶吗?您没有发现?Bombshell 是此发现?

我必须承认我发现此请求特殊在极端情况下,因为想不出,看一看我的程序的第一行中的任何人肯定有其他心理的障碍。

这是真的,没有所有其他工具和编程语言是相当一样方便,富有表现力的且功能强大 Perl 是说到 regexes。比其他人更适合某些正在进行大的频谱。一般情况下,具有表达 regexes 作为核心语言而不是作为一个库的一部分的语言有容易使用。所做任何操作中,比如 PCRE,就无法完成的 regexes 虽然将构建该程序以不同的方式如果您使用的 c。

其他语言将最终为 catch 向上与 Perl 现根据 regexes。我说这是因为启动 Perl 时, 人有任何类似 Perl 的 regexes。说您喜欢,但这是 Perl 显然赢得︰ 每个人都复制 Perl 的 regexes 虽然在不同的开发阶段。Perl 率先推出了几乎 (并非所有相当,但几乎) 越来越依靠现代模式在今天,无论您使用何种工具或语言的所有内容。因此最终其他人跟上。

但是它们将只追赶到 Perl 所在一段时间过去,就像现在一样。一切向前推进。在 regexes 如果没有别的问题,在 Perl 潜在顾客、 其他人后面。将在其中放置 Perl 一旦别人最后捕捉到 Perl 现?我也不知道,但我知道我们也将移动。可能我们将更接近于手工创建模式的 Perl₆ 的样式.

如果像这样的事情,但想要在 Perl₅ 中使用它,您可能感兴趣Damian Conway奇妙Regexp::Grammars模块。它是完全超,并使所做这里我在程序中看起来只是像基元如我使人们无需空白或字母标识符一起填塞的模式。试试看 !


简单的 HTML Chunker

这是对我此过帐的开头显示从核心分析程序完整的源代码。

建议,应使用此参数在经过严格的测试并分析类。但是我厌倦了伪装,没有人可以解析 HTML 与 regexes 只是因为他们不能的人。清楚地可以而该程序是该断言的证据。

当然,它不容易,但可能的 !

尝试这样做,是严重浪费时间,因为好分析类存在哪些您应该使用该任务。人们尝试分析任意HTML 的正确答案是是不可能。这就是一个 facile 和 disingenuous 的答案。正确和诚实的答案是,他们不应尝试它因为它是太急着找出从零开始;他们不应该中断及其后希望 reïnvent 轮的效果非常好。

另一方面,在可预见性的子集内的 HTML 是极其容易使用 regexes 分析。这也的难怪人们尝试使用它们,因为小问题,也许是玩具的问题,都没能更容易。这就是为什么它是如此重要,以区分这两个任务 — — 特定 vs 一般 — — 因为这些并不一定需要相同的方法。

我希望将来这里看到更公平和诚实处理 HTML 和 regexes 有关的问题。

这里是我的 HTML 词法分析器。它不会尝试执行验证的分析;它只标识的词法元素。您可能认为它更作为HTML chunker比 HTML 分析器。尽管在该方向做一些非常小的补助不折断的 html,规定很宽松。

即使您自己永远不会解析完整 HTML (和您为什么应? 是已解决的问题 !),该程序有很多很酷的正则表达式位,我相信很多人可以从很多了解。尽情享受 !

#!/usr/bin/env perl
#
# chunk_HTML - a regex-based HTML chunker
#
# Tom Christiansen <tchrist@perl.com
#   Sun Nov 21 19:16:02 MST 2010
########################################

use 5.012;

use strict;
use autodie;
use warnings qw< FATAL all >;
use open     qw< IN :bytes OUT :utf8 :std >;

MAIN: {
  $| = 1;
  lex_html(my $page = slurpy());
  exit();
}

########################################################################
sub lex_html {
    our $RX_SUBS;                                        ###############
    my  $html = shift();                                 # Am I...     #
    for (;;) {                                           # forgiven? :)#
        given ($html) {                                  ###############
            last                when (pos || 0) >= length;
            printf "@%d=",          (pos || 0);
            print  "doctype "   when / G (?&doctype)  $RX_SUBS  /xgc;
            print  "cdata "     when / G (?&cdata)    $RX_SUBS  /xgc;
            print  "xml "       when / G (?&xml)      $RX_SUBS  /xgc;
            print  "xhook "     when / G (?&xhook)    $RX_SUBS  /xgc;
            print  "script "    when / G (?&script)   $RX_SUBS  /xgc;
            print  "style "     when / G (?&style)    $RX_SUBS  /xgc;
            print  "comment "   when / G (?&comment)  $RX_SUBS  /xgc;
            print  "tag "       when / G (?&tag)      $RX_SUBS  /xgc;
            print  "untag "     when / G (?&untag)    $RX_SUBS  /xgc;
            print  "nasty "     when / G (?&nasty)    $RX_SUBS  /xgc;
            print  "text "      when / G (?&nontag)   $RX_SUBS  /xgc;
            default {
                die "UNCLASSIFIED: " .
                  substr($_, pos || 0, (length > 65) ? 65 : length);
            }
        }
    }
    say ".";
}
#####################
# Return correctly decoded contents of next complete
# file slurped in from the <ARGV> stream.
#
sub slurpy {
    our ($RX_SUBS, $Meta_Tag_Rx);
    my $_ = do { local $/; <ARGV> };   # read all input

    return unless length;

    use Encode   qw< decode >;

    my $bom = "";
    given ($_) {
        $bom = "UTF-32LE" when / ^ xFf xFe       /x;  # LE
        $bom = "UTF-32BE" when / ^       xFe xFf /x;  #   BE
        $bom = "UTF-16LE" when / ^ xFf xFe           /x;  # le
        $bom = "UTF-16BE" when / ^ xFe xFf           /x;  #   be
        $bom = "UTF-8"    when / ^ xEF xBB xBF      /x;  # st00pid
    }
    if ($bom) {
        say "[BOM $bom]";
        s/^...// if $bom eq "UTF-8";                        # st00pid

        # Must use UTF-(16|32) w/o -[BL]E to strip BOM.
        $bom =~ s/-[LB]E//;

        return decode($bom, $_);

        # if BOM found, don't fall through to look
        #  for embedded encoding spec
    }

    # Latin1 is web default if not otherwise specified.
    # No way to do this correctly if it was overridden
    # in the HTTP header, since we assume stream contains
    # HTML only, not also the HTTP header.
    my $encoding = "iso-8859-1";
    while (/ (?&xml) $RX_SUBS /pgx) {
        my $xml = ${^MATCH};
        next unless $xml =~ m{              $RX_SUBS
            (?= encoding )  (?&name)
                            (?&equals)
                            (?&quote) ?
            (?<ENCODING>    (?&value)       )
        }sx;
        if (lc $encoding ne lc $+{ENCODING}) {
            say "[XML ENCODING $encoding => $+{ENCODING}]";
            $encoding = $+{ENCODING};
        }
    }

    while (/$Meta_Tag_Rx/gi) {
        my $meta = $+{META};

        next unless $meta =~ m{             $RX_SUBS
            (?= http-equiv )    (?&name)
                                (?&equals)
            (?= (?&quote)? content-type )
                                (?&value)
        }six;

        next unless $meta =~ m{             $RX_SUBS
            (?= content )       (?&name)
                                (?&equals)
            (?<CONTENT>         (?&value)    )
        }six;

        next unless $+{CONTENT} =~ m{       $RX_SUBS
            (?= charset )       (?&name)
                                (?&equals)
            (?<CHARSET>         (?&value)    )
        }six;

        if (lc $encoding ne lc $+{CHARSET}) {
            say "[HTTP-EQUIV ENCODING $encoding => $+{CHARSET}]";
            $encoding = $+{CHARSET};
        }
    }

    return decode($encoding, $_);
}
########################################################################
# Make sure to this function is called
# as soon as source unit has been compiled.
UNITCHECK { load_rxsubs() }

# useful regex subroutines for HTML parsing
sub load_rxsubs {

    our $RX_SUBS = qr{
      (?(DEFINE)

        (?<WS> s *  )

        (?<any_nv_pair>     (?&name) (?&equals) (?&value)         )
        (?<name>             (?=  pL ) [w:-] +             )
        (?<equals>          (?&WS)  = (?&WS)    )
        (?<value>           (?&quoted_value) | (?&unquoted_value) )
        (?<unwhite_chunk>   (?: (?! > ) S ) +                    )

        (?<unquoted_value>  [w:-] *                             )

        (?<any_quote>  ["']      )

        (?<quoted_value>
            (?<quote>   (?&any_quote)  )
            (?: (?! k<quote> ) . ) *
            k<quote>
        )

        (?<start_tag>       < (?&WS)      )
        (?<html_end_tag>      >           )
        (?<xhtml_end_tag>   / >           )
        (?<end_tag>
            (?&WS)
            (?: (?&html_end_tag)
              | (?&xhtml_end_tag) )
         )

        (?<tag>
            (?&start_tag)
            (?&name)
            (?:
                (?&WS)
                (?&any_nv_pair)
            ) *
            (?&end_tag)
        )

        (?<untag> </ (?&name) > )

        # starts like a tag, but has screwed up quotes inside it
        (?<nasty>
            (?&start_tag)
            (?&name)
            .*?
            (?&end_tag)
        )

        (?<nontag>    [^<] +            )

        (?<string> (?&quoted_value)     )
        (?<word>   (?&name)             )

        (?<doctype>
            <!DOCTYPE
                # please don't feed me nonHTML
                ### (?&WS) HTML
            [^>]* >
        )

        (?<cdata>   <![CDATA[     .*?     ]]    > )
        (?<script>  (?= <script ) (?&tag)   .*?     </script> )
        (?<style>   (?= <style  ) (?&tag)   .*?     </style> )
        (?<comment> <!--            .*?           --> )

        (?<xml>
            < ? xml
            (?:
                (?&WS)
                (?&any_nv_pair)
            ) *
            (?&WS)
            ? >
        )

        (?<xhook> < ? .*? ? > )

      )

    }six;

    our $Meta_Tag_Rx = qr{                          $RX_SUBS
        (?<META>
            (?&start_tag) meta 
            (?:
                (?&WS) (?&any_nv_pair)
            ) +
            (?&end_tag)
        )
    }six;

}

# nobody *ever* remembers to do this!
END { close STDOUT }

两个突出显示从您的评论"使用分析类所有的时间,尤其是我还没有生成自己的 HTML。"和"模式并不一定是丑陋的他们不一定要硬。如果创建丑陋的模式,是您,不它们反射。"我完全同意对您所说的是什么,所以我 revaluating 问题。谢谢了很多关于此类详细的答案

对于那些不知道,我还以为我会提到 Tom 是"编程的 Perl"(亦即 Camel 书) 和顶部的 Perl 机构之一的共同作者。如果您怀疑这是真实的 Tom Christiansen,回过头来阅读公告。

总而言之︰ 正则表达式的是名不符实。我觉得很可惜,但它不会更改。不允许拒绝非常规语言兼容的正则表达式引擎。他们因此不能正确地实现与仅 Finte 状态机。关于计算类的功能强大的概念并不适用。正则表达式的使用不能保证 o (n) 执行时间。正则表达式的优点是简洁的语法,并暗示的域的字符识别。对我来说,这是慢速移动火车残骸,不可能看起来远离,但打开的可怕后果。

@tchrist,这永远不会回答 OPs 原始问题。分析正确的术语吗?Afaics 正则表达式执行将拆分为标记/词法分析,但最终分析通过 Perl 代码,不是正则表达式本身。

@tchrist 非常令人印象深刻。很明显是高素质、 人才 Perl 程序员,并且非常熟谙现代正则表达式。我将指出,不过,所写的内容不是真正的正则表达式 (现代、 正则,或其他),而相反的 Perl 程序,大量使用正则表达式。您的帖子确实支持正则表达式可以正确分析 HTML 的声明?还是更像Perl可以解析 HTML 的证据正确?无论如何,好样的 !

  1. 您可以编写类似 tchrist 的一部小说吗
  2. 可以使用 DOM 库,加载 HTML 和使用 xpath 并只需使用//input[@type="hidden"]或如果您不想使用 xpath,只需获取所有的输入然后筛选哪些均为隐藏状态getAttribute.

我更喜欢 #2。

<?php

$d = new DOMDocument();
$d->loadHTML(
    '
    <p>fsdjl</p>
    <form><div>fdsjl</div></form>
    <input type="hidden" name="blah" value="hide yo kids">
    <input type="text" name="blah" value="hide yo kids">
    <input type="hidden" name="blah" value="hide yo wife">
');
$x = new DOMXpath($d);
$inputs = $x->evaluate('//input[@type="hidden"]');

foreach ( $inputs as $input ) {
    echo $input->getAttribute('value'), '<br>';
}

结果︰

hide yo kids<br>hide yo wife<br>

比较了我点,实际。我想要显示它是如何硬。

那里很好的东西。我真的希望人们将显示如何更容易地使用语法分析类,这样,谢谢 !我只是想要一个工作示例,您需要仔细检查,要做到从零开始使用 regexes 极端困难。我当然希望大多数人用于 prefab 分析器一般 HTML 而不是他们自己的结论。Regexes 是复杂性的仍然非常适合他们,做自己,简单的 HTML,因为所摒弃的 99.98%。

什么很棒的阅读那些 2 非常有趣方法后将会比较速度/内存使用情况/CPU 与另一种方法 (即基于正则表达式的 VS 分析类)。

Tom Christiansen 词法分析器解决方案的气氛,这里是一个指向 Robert Cameron 似乎忘记 1998年的文章中, REX: XML 浅层分析与正则表达式。

http://www.cs.sfu.ca/~cameron/REX.html

摘要

XML 的语法非常简单,就可能解析 XML 文档到使用单个正则表达式及其标记和文本项的列表。这类浅层分析 XML 文档可以建造各种轻量级的 XML 处理工具非常有用。然而,复杂的正则表达式是难构造和阅读变得更加困难。使用懂编程的一种形式的正则表达式,此纸质文档一套 XML 浅层分析表达式可用于基础简单、 正确、 有效、 可靠且独立于语言的 XML 浅层分析。此外提供了完整的浅表分析器实现的不到 50 行每个 Perl、 JavaScript 和 Lex/弹性。

如果您喜欢阅读有关正则表达式,Cameron 的纸张是耐人寻味。他写作是简明,全面,非常详细。他不是简单地向您展示如何构造 REX 正则表达式,而且还从几个小部分任何复杂的正则表达式构建的一种做法。

我一直在使用 REX 正则表达式并关闭十年来解决的问题种类初始海报询问有关 (如何根据此特定的标记,但没有一些其他非常相似的标记?)。我发现他开发是完全可靠的正则表达式。

REX 是文档的特别有用,当您开始关注词法详细信息,例如,当将一种类型的文本文档 (例如,纯文本的 SGML XML、 HTML) 转换成另一个,其中文档可能不是文档的有效的格式正确,或甚至可用于转换的大多数分析。它允许您目标而不会影响文档其余部分群岛的标记文档中的任意位置。

我喜欢这些答案的其余部分的内容,而他们确实没有直接或作为正确回答问题。即使白金的答案是很复杂,和效率也较低。因此,我不得不放这。

我当正确使用正则表达式,巨大 proponent。但是,由于必须 (和性能),我总是状态良好格式的 XML 或 HTML 应该使用 XML 分析器。而更好的性能将是字符串分析,尽管可读性如果深度太出手之间没有一条线。但是,这不是问题。问题在于如何匹配隐藏类型的输入的标记。答案是︰

<input[^>]*type="hidden"[^>]*>

根据您的口味,您将需要包括的唯一的正则表达式选项是 ignorecase 选项。

<input type='hidden' name='Oh, <really>?' value='Try a real HTML parser instead.'>

您的示例是自结束。应当以结束 / >。此外,虽然>名称字段中的可能性几乎没有,就确实可能操作处理程序中有>例如︰ 内联 javascript 调用 OnClick 属性。如此,对于那些,具有 XML 分析器,但对于那些还有 Regex 太我文档 XML 分析器来处理,但正则表达式可以弄乱。此外,这并不是什么问题。您将永远不会运行到隐藏的输入,这些情况下,我的答案是最好的。Ya, <really>!.

/>将 XML ism;它不需要在任何版本的 HTML、 XHTML (这永远不会真正获得多大的吸引力,并已由 HTML5 以外的所有取代) 除外。您说对了大量杂乱不-真正的有效的 HTML,但良好的 HTML (没有XML) 分析器应该能够对付大部分如果他们不这样做,很可能既不将浏览器。

如果只分析或搜索所需的单个命中返回隐藏的输入字段的集合,此正则表达式会完美。使用.NET XML 文档以或引用 thrid 方 XML/HTML 分析器只需调用一种方法是大材小用当正则表达式内置的。和您说的没错,那么乱了,很好的 HTML 分析器不可能处理的网站甚至不是开发者关注。但我的公司是移交数以百万计的每月的页进行串联,jacked 在很多方面如有时 (不总是),正则表达式是最佳选择。

唯一的点是我们不能确定整个公司的原因此开发人员希望此答案。但他的要求的。

请输入您的翻译

Regular expression pattern not matching anywhere in string

确认取消