2015-04-04 72 views
-2

我有一个包含代码的多行$string。我想用&lt;&gt;替换所有的<>字符,但是在反引号内部。替换<与<无处不在,但在反引号内

例子:

Here a < and a ` some foo < stuff` 

输出:

Here a &lt; and a ` some foo < stuff` 

什么来实现它在Perl中最简单的方法?

+1

你尝试过什么?有几种方法来实现这一点,其中很多将被不同的人认为是容易的。 – 2015-04-04 13:32:59

+0

反引号可以包含多个“<”符号,或者序列总是*反引号*,*小于*,*反引号*? – Borodin 2015-04-04 13:34:04

+0

@MarcusMüller我用一个简单的正则表达式来递归地匹配ouside配对的反引号。代码太可怕了。另一种方法是解析字符串一次,提取非贪婪的反向字符串,用标记替换它们,在任何地方进行替换,并恢复被反拨的字符串。 – nowox 2015-04-04 13:40:49

回答

2

您还没有很好地定义您的问题,但是这会替换所有既不立即也不立即跟随反斜杠的<标志。

use strict; 
use warnings; 

while (<DATA>) { 
    s/(?<!`)<(?!`)/&lt;/g; 
    print; 
} 

__DATA__ 
Here a < and a `<` and Here a < and a `<` 
Here a < and a `<` 

输出

Here a &lt; and a `<` and Here a &lt; and a `<` 
Here a &lt; and a `<` 

更新

好了,你可以有反引号内的任何数据,包括换行符(我想,但你似乎不愿意说)如果你把整个文件读入一个标量变量,处理起来就容易多了。

这可以通过查找所有反向附加的子字符串或小于号<,并用&lt;替换前者。

use strict; 
use warnings; 

my $data = do { 
    local $/; 
    <DATA>; 
}; 

$data =~ s{ (`[^`]*`) | < }{ $1 // '&lt;' }egx; 
print $data; 

__DATA__ 
Here a < and a ` some foo < stuff` 
Here a < and a ` some foo < 
stuff` 
Here a < and a ` some foo < stuff` 

输出

Here a &lt; and a ` some foo < stuff` 
Here a &lt; and a ` some foo < 
stuff` 
Here a &lt; and a ` some foo < stuff`