2014-07-05 39 views
0

考虑一个测试字符串像是标记化忽略转义字符

Irrelevant start|group 1|group 2 with \| escaped|group 3|group 4|Irrelevant end 

这怎么能使用单一的Java正则表达式,提取全部由棒分离群体进行解析Java的正则表达式中间的转义栏(\ |),以及不相关的开始和结束部分(不包含栏)?与背后断言,已建议在earlier question

一个问题,就是在Java不允许变长字符串和上述团体没有预定义的

+0

不要为此使用正则表达式。请不要。像优秀的OpenCSV一样使用CSV解析库。 –

+0

这是一个非常好的主意,我也考虑过这个主意。更快,是逐字读取字符串,并在飞行中分割。这是我目前正在做的。 – PNS

+0

也在正则表达式中。 – PNS

回答

2

你可以用split做到这一点。我们想要在|之前进行拆分,但前面没有\。我们必须在我们的正则表达式中跳转|以匹配|,而不是将其用作or。为了匹配我们的正则表达式中的文字\(负面的背后),我们需要\\\\

import java.util.Arrays; 

public class Test { 

    public static void main(String[] args) { 
     String str = "Irrelevant start|group 1|group 2 with \\| escaped|group 3|group 4|Irrelevant end"; 
     System.out.println(str); 

     String[] arr = str.split("(?<!\\\\)\\|"); 

     String[] new_arr = Arrays.copyOfRange(arr, 1, arr.length - 1); 
     System.out.println(Arrays.toString(arr)); 
     System.out.println(Arrays.toString(new_arr)); 

    } 
} 

输出:

Irrelevant start|group 1|group 2 with \| escaped|group 3|group 4|Irrelevant end 
[Irrelevant start, group 1, group 2 with \| escaped, group 3, group 4, Irrelevant end] 
[group 1, group 2 with \| escaped, group 3, group 4] 

对于负看看一个简单的例子的背后,让我们看一看(?<!a)b。这与b相匹配,但前面没有a。在我们的例子中,我们想要匹配一个文字\而不是一个a|而不是一个b,这就是为什么我们需要所有的\。有很多资源可供浏览,但here是一个如果你想进一步阅读。


此外,鲍里斯蜘蛛指出,这是脆弱的,有些情况下,它将无法正常工作。与不应该用正则表达式解析XML类似,CSV格式通常应该与解析库一起使用。

+1

那么前面加一个反斜杠的管道呢?如果该反斜杠也逃脱了呢?除非创建脆弱代码的目的,否则这不是正则表达式的任务。 –

+0

您遗漏的一点是您使用的是负面后视。 –

+0

鲍里斯,我同意它很脆弱。大卫,我添加了一些关于负面后视的更多细节。感谢您的评论! – chilemagic

1

此外马特的答案,我认为这是一个非常不错的主意,如果你仍然有兴趣在正则表达式,你可以用这一个:

([\w ]+(\\\|[\w ]+)?) 

在这里,您可以检查工作的例子:

http://regex101.com/r/hK3fD3/1

正如你可以看到每个比赛的每个第一组包含相关的内容,你可以放弃第一场和最后一场比赛。

希望能帮到