将包含值范围的字符串解析为最小和最大变量v2

时间:2009-11-23 11:47:36

标签: php

我需要根据以下规则将字符串解析为两个变量,并且我正在寻找在PHP中实现此目的的最佳方法:

"40.3" -> minval=40.3, maxval=40.3
"-40.3" -> minval=-40.3, maxval=-40.3
"40.3-60.76" -> minval=40.3, maxval=60.76
"-40.3-60.76" -> minval=-40.3, maxval=60.76
"-60.76--40.3" -> minval=-60.76, maxval=-40.3

不幸的是,我必须使用减去负值和范围分隔符。

这与我之前的问题非常相似:

Parse string containing range of values to min and max variables

(我已经发布了第二个问题,但发现我弄乱了桌子。希望现在好了。)

5 个答案:

答案 0 :(得分:5)

尽管我试图避免使用正则表达式,但在这种情况下我会使用一个。我认为这应该匹配你所有的字符串:

preg_match('/^(?P<min>-?\d+(\.\d+)?)(-(?P<max>-?\d+(\.\d+)?))?/', $string, $matches);
$min = $matches['min'];
if (isset($matches['max'])) {
     $max = $matches['max'];
}

(正则表达式的长度是在日常编码中避免它们的一个很好的理由)

答案 1 :(得分:5)

遇到这样的问题时,你可以尝试用某种Backus-Naur形式表达它:

Range := Number | Number "-" Number
Number := Sign Digits
Sign := "" | "-"
Digits := Digit* | Digit* "."  Digit*

并从中创建正则表达式。

答案 2 :(得分:2)

如果您不想使用正则表达式,此函数将执行此操作:

function parse_range($range) {
    list($from, $to) = explode('-', substr($range, 1), 2);
    $from = $range[0] . $from;
    if (!$to and $to !== '0') {
        $to = $from;
    }
    return array($from * 1, $to * 1);
}

答案 3 :(得分:1)

$test = array(
  "40.3",
  "-544",
  "40.3-60",
   "-40.1234-60.76",
  "-60.76--40.3",

);

$num = "(-?\d+(?:\.\d+)?)";
$re = "~^$num-?$num?$~";
foreach($test as $test) {
    if(preg_match($re, $test, $m)){
       if(!isset($m[2])) $m[2] = $m[1];
       echo "from $m[1] to $m[2]\n";
    }
}

答案 4 :(得分:1)

这在测试中运作良好:

<?php
preg_match("/^(\-{0,1}[0-9\.])\-{0,1}(\-{0,1}[0-9\.]*)\$/", "-1-2", $matches);
$min = $matches[1];
$max = $matches[2] ? $matches[2] : $min;
?>