正则表达式满足3个独立的案例

时间:2017-09-25 18:55:15

标签: regex regex-lookarounds regex-greedy regex-group

我正在试图找出一个可以与java的String.split(正则表达式)一起使用的正则表达式,以便从文件中获取“行”数组。

回车不定义行的结尾,而是逗号,但不是所有逗号。如果逗号位于括号,单引号或注释(/ *注释,更多注释* /)之间,则它不表示行的结尾。

示例:

1 test fixed(5,2)
2 another_test char(12)
2 a_third_test
3 one pic'9{9}V.99'
3 two pic'9,999V.99'
3 three fixed(7,2)
/* test,t*//*test 2,*//*and more */  2 another_field fixed bin(13)
2 a_really_long_super_long_field_name_requiring_two_lines_for_declaration
    char(1)
2 a_field char(8)

预期输出为(为了清晰起见,省略了\ t和额外的空格):

,(?![^(]*\))

我想出了3个独立的正则表达式来获得3个部分:

  • (,(?![^']*')) - 所有逗号都不在括号中
  • (,(?![^\/\*]*\*\/)) - 所有逗号都不在单引号中
  • (.*?)|(,)|'.*?'|(,)|\/*.*?*\/|(,) - 所有逗号都不在评论中

我尝试使用或1 test fixed 2 another_test char 2 a_third_test 3 one pic 3 two pic 3 three fixed 2 another_field fixed bin 2 a_really_long_super_long_field_name_requiring_a_line_break_... char 2 a_field char 加入他们,但获得以下内容:

String temp = "";
for(String line:text.split("\n")){
  if(line.trim().charAt(line.trim().length()-1) == ',' || line.trim().charAt(line.trim().length()-1) == ';'){
    System.out.println(temp + line);
    temp = "";
  } else {
    temp += line.trim();
  }
}

有没有办法可以将这3个正则表达式(或者有更好的表达式?)组合起来找到满足所有3个的正则表组?

更新:

我可以通过一些简单的java来完成确切的事情,但我想用正则表达式作为学术上的追随者。

def func(self, n):
    Arr = [random.randint(0, 2 ** 16) for _ in range(n)]
    Arr = list(set(Arr))
    Arr = [('{0:0' + str(16) + 'b}').format(x) for x in Arr]
    Arr = np.asarray([list(map(int, list(x))) for x in Arr])
    return Arr

1 个答案:

答案 0 :(得分:0)

我想你可能会过度思考这一点。重要的是要记住正则表达式用于解析regular languages。当你需要检查你是否在评论或其他内容中以了解逗号的含义时,你所看到的是context-sensitive language(见下图)。

By J. Finkelstein (Own work) [CC BY-SA 3.0 (https://creativecommons.org/licenses/by-sa/3.0)], via Wikimedia Commons

  

作者J. Finkelstein(自己的作品)[CC BY-SA 3.0(https://creativecommons.org/licenses/by-sa/3.0

话虽如此,在一行末尾匹配逗号和分号很容易。 /\s*(.*?)[,;]$/gsm适用于您问题中的测试输入。但是,这没有考虑像

这样的东西
test fixed(5,2),
/* a,
   multi-line,
   comment,
*/

在我看来,解决这个问题的最佳选择是在开始使用\/\*.*?\*\/进行解析之前放弃评论。如果你需要保留评论,你可能会使用负面的外观,但这些效率非常低,你最好不要编写一个标记器/解析器。