具有独特任意值的全局正则表达式替换

时间:2011-10-14 13:12:16

标签: regex perl bash

我有一个包含许多链接的大型HTML文件,即<a href="...">。我需要用唯一的任意值替换每个href。因此,替换后第一个链接为<a href="http://link1">,第二个链接为<a href="http://link2">,依此类推。

我们可以使用正则表达式吗?或者,我是否需要编写一个小脚本来扫描文件?理想情况下,解决方案将是Perl或bash脚本(不是专有的)。

感谢。

3 个答案:

答案 0 :(得分:2)

Perl可能是你最好的选择,但我不会尝试在一个正则表达式中进行(甚至可能不可能)。我认为这只是你可以制作剧本的同时还能让它变得可读:

#!/usr/bin/perl
$link = 1;
while(<>) {
    $link++ while( s/href="(?!link\d)[^"]*"/href="link$link"/ );
    print;
}

然后这样称呼它:

./thatScript.pl inputFile.html > newInputFile.html

它将检查每一行输入,并且对于它找到的每个href="...",将其替换为带编号的链接并递增链接号。还有一个负面的预测,以避免连续替换相同的href

编辑:仅仅是为了它,这就是你如何将上述内容压缩成一行bash:

perl -pe '$link++ while( s/href="(?!link\d)[^"]*"/href="link$link"/ )' inFile.html > outFile.html

这使用了Perl令人惊叹的-p标记,如here所述。

答案 1 :(得分:1)

我绝对不推荐这个(tchrist是对的,当然,它应该是一个脚本)但它确实具有以确定性/可重复的方式简洁和满足字面要求而不需要保存状态的优点/映射。

perl -MDigest::MD5=md5_hex -MXML::LibXML -le '$d = XML::LibXML->load_html( location => shift || die "need location" ); for $a ( $d->findnodes("//\@href") ) { $a->setValue( md5_hex $a->value ) }; print $d->serialize' targeted.html

答案 2 :(得分:0)

未经测试的:

perl -pe 's{(href=")[^"]+}{$1 . "http://link" . ++$count}ge' filename > newfile