我尝试在命令行中使用perl中的负前瞻:
echo 1.41.1 | perl -pe "s/(?![0-9]+\.[0-9]+\.)[0-9]$/2/g"
以获得如下所示的增量版本:
1.41.2
但它只是返回我:
![0-9]+\.[0-9]+\.: event not found
我在regex101(PCRE)中试过,它工作正常,所以我不确定为什么它在这里不工作
s6fujrry1#
在Bash中,!是“历史扩展字符”,除非用反斜杠或单引号转义(双引号 * 不 * 禁用此功能;也就是说,支持在双引号内展开历史记录。请参阅Difference between single and double quotes in Bash)因此,只需将双引号改为单引号:
!
echo 1.41.1 | perl -pe 's/(?![0-9]+\.[0-9]+\.)[0-9]$/2/g'
瞧:
kt06eoxx2#
我猜下面这个表达式也可以:
([0-9.]+)\.([0-9]+)
测试
perl -e' my $name = "1.41.1"; $name =~ s/([0-9.]+)\.([0-9]+)/$1\.2/; print "$name\n"; '
nbnkbykc3#
如果您想“increment”一个数字,那么您不能硬编码新的值,但需要捕获那里的内容并递增它
echo "1.41.1" | perl -pe's/[0-9]+\.[0-9]+\.\K([0-9]+)/$1+1/e'
这里/e修饰符使得替换的一方作为代码来计算,我们可以+1捕获的数字,然后替换。\K丢弃先前的匹配,所以我们不需要把它们放回去;请参阅perlre中扩展模式中的“*LookaroundAssert *”。有时候,查看器正是你想要的,但是它们增加了正则表达式的复杂性(仅仅是因为它们存在),可能很难得到正确的结果,并且降低了效率。您得到的奇怪输出是因为Perl程序周围使用的双引号“邀请”shell查看内部内容,从而将!解释为历史扩展并运行它,如ruakh的帖子中所解释的那样。
/e
+1
\K
f1tvaqid4#
作为lookahead的替代方法,我们可以使用捕获组,例如,下面将把版本号捕获到3个捕获组中。
(\d+)\.(\d+)\.(\d+)
如果要按原样输出捕获的版本号,则应为:
\1.\2.\3
如果用数字“2”替换第三部分,则为:
\1.\2.2
为了适应OP的问题,它将是:
$ echo 1.14.1 | perl -pe 's/(\d+)\.(\d+)\.(\d+)/\1.\2.2/' 1.14.2 $
4条答案
按热度按时间s6fujrry1#
在Bash中,
!
是“历史扩展字符”,除非用反斜杠或单引号转义(双引号 * 不 * 禁用此功能;也就是说,支持在双引号内展开历史记录。请参阅Difference between single and double quotes in Bash)因此,只需将双引号改为单引号:
瞧:
kt06eoxx2#
我猜下面这个表达式也可以:
测试
输出
Please see the demo here.(第一个字母)
nbnkbykc3#
如果您想“increment”一个数字,那么您不能硬编码新的值,但需要捕获那里的内容并递增它
这里
/e
修饰符使得替换的一方作为代码来计算,我们可以+1
捕获的数字,然后替换。\K
丢弃先前的匹配,所以我们不需要把它们放回去;请参阅perlre中扩展模式中的“*LookaroundAssert *”。有时候,查看器正是你想要的,但是它们增加了正则表达式的复杂性(仅仅是因为它们存在),可能很难得到正确的结果,并且降低了效率。
您得到的奇怪输出是因为Perl程序周围使用的双引号“邀请”shell查看内部内容,从而将
!
解释为历史扩展并运行它,如ruakh的帖子中所解释的那样。f1tvaqid4#
作为lookahead的替代方法,我们可以使用捕获组,例如,下面将把版本号捕获到3个捕获组中。
如果要按原样输出捕获的版本号,则应为:
如果用数字“2”替换第三部分,则为:
为了适应OP的问题,它将是: