匹配一组匹配中的第一个字符

时间:2011-08-29 23:47:17

标签: php regex

我有日期格式的字符串,其中包含Y,M和D.例如,某些格式可能是:

YY-MM-DD
M-D-Y G
MM/Y/DD
(etc)

我想在这样的字符串上运行正则表达式匹配并按顺序提取Y,M,D。例如,在上面,我想:

array('Y', 'M', 'D');
array('M', 'D', 'Y');
array('M', 'Y', 'D');
(etc)

我写过这个正则表达式:

/(m+)|(d+)|(y+)/

但问题是它返回整个匹配而不是第一个字符:

array('YY', 'MM', 'DD');
array('M', 'D', 'Y');
array('MM', 'Y', 'D');
(etc)

如何编写表达式以便它只返回第一个字符?

编辑:一些代码(真的没什么复杂的。)

$dates = array('YY-MM-DD', 'M-D-Y G', 'MM/Y/DD');

foreach($dates as $date){
   preg_match_all('/(m+)|(d+)|(y+)/', strtolower($date), $matches);
   var_dump($matches);
}

4 个答案:

答案 0 :(得分:1)

我不擅长正则表达式。但是下面的代码可以解决您的问题,直到找到更好的正则表达式字符串。

$dates = array('YY-MM-DD', 'M-D-Y G', 'MM/Y/DD');
$result = array();

foreach($dates as $date){
   preg_match_all('/([m])[mdy]?|([d])[mdy]?|([y])[mdy]?/i', $date, $matches);

   $tmp = array();
   for($i=1;$i<=3;$i++){
       foreach($matches[$i] as $m){
            if(!empty($m)){
                $tmp[] = $m;
                break;
            }
       }
   }
   $result[] = $tmp;
}

答案 1 :(得分:1)

在我看来,/\b[ymd]/就是您所需要的:

$dates = array('YY-MM-DD', 'M-D-Y G', 'MM/Y/DD');

foreach($dates as $date){
   preg_match_all('/\b[ymd]/', strtolower($date), $matches);
   var_dump($matches);
}

编辑:这里也是一个处理YYYYMMDD的人:

/(?<!y)y|(?<!m)m|(?<!d)d/

输出:

array(1) {
  [0]=>
  array(3) {
    [0]=>
    string(1) "y"
    [1]=>
    string(1) "m"
    [2]=>
    string(1) "d"
  }
}
array(1) {
  [0]=>
  array(3) {
    [0]=>
    string(1) "m"
    [1]=>
    string(1) "d"
    [2]=>
    string(1) "y"
  }
}
array(1) {
  [0]=>
  array(3) {
    [0]=>
    string(1) "m"
    [1]=>
    string(1) "y"
    [2]=>
    string(1) "d"
  }
}

答案 2 :(得分:0)

我认为这个更好:收集正则表达式的第一个字母。但我假设只有“ - ”,“/”和“\”字符可以出现在M,D,Y之间。如果需要,您可以添加更多。

$dates = array('YY-MM-DD', 'M-D-Y G', 'MM/Y/DD');
$result = array();

foreach($dates as $date){

   preg_match_all('/([mdy])[a-z0-9\ \-\/\\\]?/i', $date, $matches);
   $result[] = $matches[1];

}

答案 3 :(得分:0)

尝试制作这样的正则表达式:

/(m)m*|(d)d*|(y)y*/

它只捕获第一个字母,但允许更多。