2010-03-21 72 views
1

我有一个测试列表,我试图捕获使用正则表达式的数据。用于捕获编号文本列表的正则表达式

这里是文本格式的一个样本:

(1) this is a sample string /(2) something strange /(3) another bit of text /(4) the last one/ something!/ 

我目前正确抓住了这个正则表达式,但我有一些困难使得它异常的条件下工作。

这里是我的正则表达式

/\(?\d\d?\)([^\)]+)(\/|\z)/ 

不幸的是一些数据包含圆括号这样的:

(1) this is a sample string (1998-1999) /(2) something strange (blah) /(3) another bit of text /(4) the last one/ something!/ 

的子 '(1998- 1999年)' 和 '(等等)' 使其失败!

任何人都在意在这一个裂缝? 谢谢:d

+0

你没有说究竟正则表达式应该捕捉到。 – user187291 2010-03-21 13:52:53

+0

对不起,更具体。我正在审查现在的答案急(至少2看起来正确)*咧嘴*我试图捕获我的示例捕获的文本(即英文文本减去编号)。 – pchap10k 2010-03-21 13:58:40

回答

1

我想试试这个:

\((\d+)\)\s+(.*?)(?=/(?:\(\d+\)|\z)) 

这相当可怕的期待正则表达式执行以下操作:

  • 它看起来对包裹在括号中的一个或多个数字和捕捉他们。
  • 圆括号中的数字后面必须至少有一个空格字符。这个白色空间被忽略(未被捕获);
  • 使用非贪婪通配符表达式。这是(imho)对于这类问题使用负面字符组(例如[^/]+)的最佳方式;
  • 阳性先行((?=...))表示,表达式必须跟反斜杠然后之一: 包裹在括号
    • 一个或多个数字;或
    • 字符串终止符。

为了让你在PHP为例(不指定语言):

$s = '(1) this is a sample string (1998-1999) /(2) something strange (blah) /(3) another bit of text /(4) the last one/ something!/'; 
preg_match_all('!\((\d+)\)\s+(.*?)(?=/(?:\(\d+\)|\z))!', $s, $matches); 
print_r($matches); 

输出:

Array 
(
    [0] => Array 
     (
      [0] => (1) this is a sample string (1998-1999) 
      [1] => (2) something strange (blah) 
      [2] => (3) another bit of text 
      [3] => (4) the last one/ something! 
     ) 

    [1] => Array 
     (
      [0] => 1 
      [1] => 2 
      [2] => 3 
      [3] => 4 
     ) 

    [2] => Array 
     (
      [0] => this is a sample string (1998-1999) 
      [1] => something strange (blah) 
      [2] => another bit of text 
      [3] => the last one/ something! 
     ) 

) 

一些注意事项:

  • 您不指定要捕获的内容URE。我已经承担了列表项目号和文本。在这种情况下,可能会错误地删除那些捕获括号。无论哪种方式,你可以得到整场比赛;
  • 我已经放弃了比赛的尾部斜线。这可能不是你的意图。再次,改变捕捉以适合;
  • 我已经允许任何数量的数字的项目编号。你的版本只允许两个。如果您喜欢这种方式,请将\d+替换为\d\d?
+0

这当然是答案的劳斯莱斯。它也很好地捕捉了Ruby中的所有内容。格式化为Ruby我使用这个... /\(\d+\).*?\/(?=\(|$)/ – pchap10k 2010-03-21 14:04:36

+0

Cletus:我刚刚注意到最后一个条目中的嵌入正斜杠正在被裁剪。我已经投票支持你了,现在我正在破译正则表达式,但是你能否建议如何在正斜杠之后包含文本?Thx – pchap10k 2010-03-21 14:11:55

+0

@crunchyt你能解释一下吗?尾随的'/',你想在第二个被捕获的组?或者你的意思是别的吗? – cletus 2010-03-21 14:16:36

1

添加前置/到字符串的开头,附加一个(0)到字符串的末尾,那么整个字符串与图案\/\(\d+\)分裂,并丢弃所述第一和最后一个空元素。

1

只要/不能出现在文本...

\(?\d?\d[^/]+ 
+0

这很接近,但我需要在数字之间的整个字符串。 – pchap10k 2010-03-21 14:03:13