假设我有一个这样的字符串:
=====
我想用这个替换它:
-----
我只想替换它,如果它有超过一定数量的那个角色(我们会说> 3)。
所以,这些应该是替代品:
=== -> ===
==== -> ----
===== -> -----
应用程序是我想用mark level替换markdown中的所有1级标题,而不更改嵌入的代码块。
我知道我可以这样做:
/=/-/g
,但这会匹配任何带有等号(if (x == y)
)的内容,这是不可取的。
或者这个:
/===+/----/g
,但这并不考虑原始匹配字符串的长度。
这可能吗?
答案 0 :(得分:10)
可以使用Perl:
my $string = "===== Hello World ====";
$string =~ s/(====+)/"-" x length($1)/eg;
# $string contains ----- Hello World ----
Flag / e使得Perl在s ///的第二部分执行表达式。 你可以尝试使用oneliner:
perl -e '$ARGV[0] =~ s/(====+)/"-" x length($1)/eg; print $ARGV[0]' "===== Hello World ===="
答案 1 :(得分:4)
根据您使用的语言而定。基本上,在某些语言中,您可以将代码放在regexp的右侧,允许您执行以下操作:(这是perl):
s/(=+)/(length($1) > 3 ? "-" : "=") x length($1)/e
'e'标志告诉perl执行表达式右侧的代码,而不是仅仅将其解析为字符串。
答案 2 :(得分:1)
我也在寻找类似这样的纯正则表达式解决方案。我在SO上找不到一个,所以我解决了。
简短版本:here是正则表达式:
((?<====)=)|(=(?====))|((?<===)=(?==))|((?<==)=(?===))
这是我使用R到达那里的方式:
str <- " = == === ==== ===== ====== ======="
gsub("=(?====)", "-", str, perl = TRUE) # (1) Pos. lookahead
gsub("(?<====)=", "-", str, perl = TRUE) # (2) Pos. look-behing
gsub("(?<===)=(?==)", "-", str, perl = TRUE) # (3) Middle part for cases of 4 or 5 ='s (1/2)
gsub("(?<==)=(?===)", "-", str, perl = TRUE) # (4) Middle part for cases of 4 or 5 ='s (2/2)
# Combining all, we have:
gsub("((?<====)=)|(=(?====))|((?<===)=(?==))|((?<==)=(?===))", "-", str, perl = TRUE) # (5)
(1) = == === -=== --=== ---=== ----===
(2) = == === ===- ===-- ===--- ===----
(3) = == === ==-= ==--= ==---= ==----=
(4) = == === =-== =--== =---== =----==
(5) = == === ---- ----- ------ -------
较不复杂的正则表达式的替代方法(但需要3个步骤)
# First, deal with 4 & 5 equal signs with negative look-behind and lookahead
str <- gsub("(?<!=)={4}(?!=)", "----", str, perl = TRUE) # (2.1)
str <- gsub("(?<!=)={5}(?!=)", "-----", str, perl = TRUE) # (2.2)
# Then use regex (3) from above for 6+ equal signs
str <- gsub("((?<====)=)|(=(?====))", "-", str, perl = TRUE) # (2.3)
(2.1) = == === ---- ===== ====== =======
(2.2) = == === ---- ----- ====== =======
(2.3) = == === ---- ----- ------ -------
答案 3 :(得分:0)
专门针对此Markdown标题用例,您可以使用以下事实:它们总是出现在行的开头:
/(^=|(?<==)=)/-/
将替换所有在行首或前面带有'='的'='字符。
虽然它将在文本中加倍'=='……也许有人可以对此进行改进?