2013-01-16 116 views
0

输入:Java正则表达式提取的标签之间的内容

<tag>Testing different formatting options in </tag><tag class="classA classB">Text</tag><tag class="classC">Class C text</tag> 

预期输出:

<tag>Testing different formatting options in </tag><tagA><tabB>Text</tagA></tagB><tagC>Class C text</tag> 

基本上标签通过基于在 “类” 的属性的标签替换。 。即,如果属性具有CLASSA属性,则标签将通过TAGA代替,如果CLASSB属性也出现,则标签也将包括TAGB等..

尝试制成:

final String TAG_GROUPS = "<tag class=\"(.*)\">(.*)</tag>"; 
    Pattern pattern = Pattern.compile(TAG_GROUPS); 
    Matcher matcher = pattern.matcher(inputString); 

我收到的输出无法找到匹配的标签。特别是声明

String classes = matcher.group(1); 

给出字符串classA classB">Text</tag><tag class="classC">Class C text</tag。模式匹配器无法找到匹配的标签。我是正则表达式的初学者,我想知道问题的正确模式。任何帮助表示赞赏。

+8

使用正则表达式解析XML很棘手,因为这篇文章阐明了:http://stackoverflow.com/a/1732454/758446 – BlackVegetable

+0

使用'。*?'而不是'。*':*? - 不情愿的版本,它尽可能少地匹配 –

回答

1

当您使用*时,它会尝试吸收所有可能的字符(贪婪)。

如果您想要.*匹配较少可能的字符,您必须使用与*?的惰性匹配。

所以,你的正则表达式得到为:

<tag class=\"(.*?)\">(.*?)</tag> 

以上,是最简单的方式。但没有必要的最佳方式。懒惰的比赛比贪婪更慢,如果可以的话,你必须尽量避免它。例如,如果你估计你的代码是正确的(没有标签没有标签损坏等),最好使用否定类而不是.*?。例如,你的正则表达式可以写为:

<tag class="([^"]*)">([^<]*)</tag> 

女巫是正则表达式引擎更有效(但并不总是能够转换懒惰匹配否定类)。

当然,如果你想要解析一个完整的html或xml文档,你必须做很多不同的修改,最好使用一个xml(html)解析器。

1

虽然您可以使用regexp来查找开始标记并解析类,但是没有办法生成嵌套标记作为输出。详情请参阅this answer

你可以做的是写你自己的简单的HTML解析器,但HTML是相当混乱的解析。或者换句话说:看看我的声誉,然后考虑如果没有一个很好的理由(比如有人给我五十万美元),我不会尝试它。

改为使用真实的HTML解析器,如HTML Tidy

2

你应该使用贪婪的正则表达式:"<tag class=\"(.*?)\">(.*)</tag>"。否则.*匹配任何字符包括</tag>

但通常我同意大家这不是使用正则表达式解析XML的最佳实践。改用XML解析器。

+2

这是不愿意的正则表达式不贪婪。贪婪默认使用没有问号。 –

+0

而你必须在第二个参数中放入懒惰(或不情愿)的正则表达式。试着解析这个例子,你会看到这个问题。 – PhoneixS

相关问题