Perl Regex:无与伦比[正则表达式;标记为< - HERE

时间:2015-03-13 10:14:00

标签: regex perl

我有一个用于从文本中提取URL的小Perl脚本:

#!/usr/bin/perl

while ( <STDIN> )
{
if ( /(http|ftp|https):\/\/([\w\-_]+(?:(?:\.[\w\-_]+)+))([\w\-\.,@?^=%&amp;./~\+#]*[\w\-\@?^=%&amp;/~\+#])?/ )
{
print;
}
}

当我在Textwrangler中搜索时,正则表达式工作正常,但是当我通过此脚本运行它时,我收到以下错误:

$ cat file.txt | perl myscript.pl
Unmatched [ in regex; marked by <-- HERE in m/(http|ftp|https)://([\w\-_]+(?:(?:\.[\w\-_]+)+))([ <-- HERE \w\-\.,@?^=%&amp;./ at myscript.pl line 5.

3 个答案:

答案 0 :(得分:5)

最后字符类中的/也需要进行转义。您可以考虑使用/x修饰符使其更具可读性,并使用不同的分隔符来避免“倾斜牙签”。另外,\w类 已经包含下划线,并且字符类中的.总是按字面意思匹配。

if (m{
        (http|ftp|https)://
        ( [\w\-]+ (?: (?:\.[\w\-]+)+ ) )
        (
          [\w\-.,@?^=%&amp;/~+#]*
          [\w\-@?^=%&amp;/~+#]
        )?
   }x
) {
    print;
}

通过这样做,也很清楚最后两个字符类是不是真正的字符类:

这:/[&amp;]*/
肯定会匹配&amp;,还会a&m&pmapa&;等等。

答案 1 :(得分:1)

由于/是正则表达式分隔符,因此您需要转义正则表达式中存在的所有正斜杠。

(http|ftp|https):\/\/([\w\-_]+(?:(?:\.[\w\-_]+)+))([\w\-\.,@?^=%&amp;.\/~\+#]*[\w\-\@?^=%&amp;\/~\+#])?

我不知道你在角色类中想要实现这个&amp是什么。此[&amp]将匹配给定列表中的单个字符,无论它可能是&还是a还是m还是p,而不是整个&amp }

答案 2 :(得分:0)

你可以使它更具可读性和可调试性,并且,我希望这可能会对你的问题有所了解。

while ( <STDIN> ) {
    print if m{
       ( http | ftp | https )://
       ( [\w\-_]+ (?: (?:\.[\w\-_]+)+ ) )
       ( 
            [\w\-\.,@?^=%&amp;./~\+#]* 
            [\w\-\@?^=%&amp;/~\+#]
       )?
   }x;

另一方面,我会达到Regexp::Common::URIURI::Find。试图修复这种模式似乎不是任何人的最佳用途。