【问题标题】:How to catch a dot in Perl regex?如何在 Perl 正则表达式中捕捉一个点?
【发布时间】:2017-01-19 18:02:33
【问题描述】:

我正在尝试执行这行代码:

  my $test = 'test .15oz test';
  $test =~ /([\d]+)([\.]?[\d]+)*oz\b/;
  print("test=$1\n");

这个的输出是:

  test=15

我想抓住那个点。我究竟做错了什么? 最好的办法是以某种方式捕捉 0.15,但现在我连一个点都抓不到。

任何有关从 regex 获得 0.15 的帮助将不胜感激,所以:

0.15 -> 0.15

.15 -> 0.15

..15 -> 0.15

0.0.0.15 -> 0.15

000.15 -> 0.15

15 -> 15

我也试过了:

$test =~ /([\d]+)(\.?[\d]+)*oz\b/;
$test =~ /([\d]+)([.]?[\d]+)*oz\b/;

但没有成功。仍然是“15”。

【问题讨论】:

  • 您不应该在字符类中使用反斜杠转义点。只在外面。所以\.[.] (还有其他风格的正则表达式在出现多余的反斜杠转义时可能会失败,所以最好避免它)。无论如何,这不是这里的问题。
  • 字符类本身似乎是多余的。
  • @blubberdiblub 感谢您的建议,但它不起作用:(
  • 使用$test =~ /(\d*\.?\d+)oz\b/;
  • @WiktorStribiżew 是的!那行得通,谢谢!这应该是一个答案。顺便提一句。我不知道为什么这个 q 被否决了

标签: regex perl pcre


【解决方案1】:

你要匹配的字符串被匹配

(?:\d+(?:\.\d+)?|\.\d+)oz

(Wiktor Stribiżew 发布了一些较短的内容,但效率要低得多。)

所以你想要

if ( my ($match) = $test =~ /(\d+(?:\.\d+)?|\.\d+)oz/ ) {
   say $match;
}

如果您的输入为.15..15,则您不可能匹配0.15。只需独立于匹配修复字符串。

$match = "0".$match if $match =~ /^\./;

同样,修剪前导零最好在匹配之外完成。

$match =~ s/^0+(?!\.)//;

我们在一起,我们得到了

if ( my ($match) = $test =~ /(\d+(?:\.\d+)?|\.\d+)oz/ ) {
   $match =~ s/^0+(?!\.)//;
   $match = "0".$match if $match =~ /^\./;
   say $match;
}

【讨论】:

    【解决方案2】:

    您正在使用第一个捕获组。在您的模式([\d]+)([\.]?[\d]+)*oz\b 中,第一个捕获组匹配一个或多个数字。要捕获oz 之前的整个浮点数或整数,请使用

    $test =~ /(\d*\.?\d+)oz\b/;
              ^         ^
    

    \d*\.?\d+ 将匹配 0+ 个数字、一个可选的点(注意它在字符类之外转义)和 1+ 个数字。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-07-11
      • 2021-09-06
      • 1970-01-01
      • 2011-12-14
      • 2021-04-25
      • 2011-02-22
      相关资源
      最近更新 更多