2011-09-12 97 views
4

我意识到这可能看起来像一个愚蠢的请求,但我会问无论如何。正则表达式第n个匹配

我想用正则表达式来查找号码列表中的每个第n个逗号,即:

88574,93243,129659,135504,136357,141052,141619,141619,142195,144622,144946,... 

则可以有每4个逗号“”替换“ \ r \ n”,从而开启将数字列表放入4行n列的网格中。

找到所有逗号很简单:

[^0-9] 

从上面的列表中会发现所有的逗号。我现在如何将这些比赛进行分组,以便每四次排除三次。

我可以用PHP preg_matches做到这一点,但我用这个与MySQL正则表达式替换函数,所以更喜欢纯正则表达式答案(如果存在)。

,我使用MySQL的功能如下:

DROP FUNCTION IF EXISTS `regex_replace`$$ 

    CREATE DEFINER=`root`@`127.0.0.1` 
    FUNCTION `regex_replace`(pattern VARCHAR(1000),replacement VARCHAR(1000),original TEXT) 
    RETURNS VARCHAR(1000) CHARSET latin1 
     DETERMINISTIC 
    BEGIN 
    DECLARE temp VARCHAR(1000); 
    DECLARE ch VARCHAR(1); 
    DECLARE i INT; 
    SET i = 1; 
    SET temp = ''; 
    IF original REGEXP pattern THEN 
    loop_label: LOOP 
     IF i>CHAR_LENGTH(original) THEN 
       LEAVE loop_label; 
     END IF; 
     SET ch = SUBSTRING(original,i,1); 
     IF NOT ch REGEXP pattern THEN 
      SET temp = CONCAT(temp,ch); 
     ELSE 
      SET temp = CONCAT(temp,replacement); 
       END IF; 
     SET i=i+1; 
       END LOOP; 
    END IF; 
    RETURN temp; 
    END$$ 

,你可以看到它的自不必处理复杂的匹配的正则表达式。因此,能够选择第n个逗号的正则表达式就足够了。

我希望这可以澄清问题。

编辑:

我已经加入了lib_mysqludf_preg图书馆的服务包含preg_replace函数的功能。这是一个针对MySQL的PCRE实现,如果我能够回答每四分之一选择正则表达式的问题,并用',\ r \ n'替换,应该可以工作。

+0

这可能是一个很好的开始分组成四个数字的集合:([0-9] * [^ 0-9]){4} –

+0

谢谢詹姆斯, 非常类似的答案以下蒂姆。请参阅对他的回复和更新的问题。 再次感谢, Fin – Fin

+1

我不会做MySQL,但如果我正在阅读您的编辑权限,您现在可以访问'preg_replace',所以@ Tim的解决方案应该是可行的。 –

回答

4
$result = preg_replace('/(?:[^,]*,){4}/', '\0\r\n', $subject); 

这符合连续4逗号分隔值(我假设你不会有一个组内的字符串里的逗号),并在他们之后增加了一个CRLF。

[编辑] 上面是基于PHP溶液

对于纯的MySQL溶液,安装lib_mysqludf_preg和使用:

SELECT preg_replace('/(?:[^,]*,){4}/', '${0}\r\n', `fieldname`) as 'new_layout' from `tablename`; 

许多由于所有贡献。

+1

感谢蒂姆蒂姆,这与我想要做的非常接近,但并不完全在那里。你的正则表达式所做的是匹配整个字符组,即'88574,93243,129659,135504',而我需要匹配每4个逗号,即: 88574,93243,129659,135504,136357,141052,141619, 141619,142195,144622,144946,177824,... 否否否是否否否是否否否是 我无法使用PHP,因为结果正在被MySQL函数处理。 我希望这是明确的 – Fin

+0

MySQL的正则表达式不符合这个任务。他们只能选择匹配或不匹配正则表达式的列。而已。 –

+0

再次感谢Tim, – Fin

1

如果你想匹配每个逗号,那么更直接的模式,也将工作。

对于匹配每隔四个逗号,如果MySQL支持后台查询,也许你可以使用(?<=(^|\r\n)(\d+,){3}\d+),。但是,这假设每次替换都是在下一场比赛之前完成的。否则,可能(?<=^((\d+,){4})*(\d+,){3}\d+),将工作。

+0

MySQL不支持lookbehind断言。更不用说无限期的重复。不过,你的正则表达式在.NET中可以正常工作。 –

+0

谢谢!那种怀疑的。虽然值得一试。 – henko

+0

感谢Henko, 最后一件事情,它只会选择第四个逗号,而不是每四分之一(四分之一)。我最后一次更新了这个问题。 – Fin