Java:replaceAll正则表达式中的古怪
我试图用Java操作一个字符串来识别 我在几位在线测试人员中测试了正则表达式,结果它成功了,但当我尝试用Java实现时,它只能识别被下划线包围的文本。我举了一个例子来说明这个问题:Java:replaceAll正则表达式中的古怪,java,regex,string,Java,Regex,String,我试图用Java操作一个字符串来识别 我在几位在线测试人员中测试了正则表达式,结果它成功了,但当我尝试用Java实现时,它只能识别被下划线包围的文本。我举了一个例子来说明这个问题: private String process(String input) { String processed = input.replaceAll("(\\b|^)\\_(.*)\\_(\\b|$)", "underscore") .replaceAll("(\\b|
private String process(String input) {
String processed = input.replaceAll("(\\b|^)\\_(.*)\\_(\\b|$)", "underscore")
.replaceAll("(\\b|^)\\*(.*)\\*(\\b|$)", "star")
.replaceAll("(\\b|^)```(.*)```(\b|$)", "backticks")
.replaceAll("(\\b|^)\\~(.*)\\~(\\b|$)", "tilde")
.replaceAll("(\\b|^)\\`(.*)\\`(\\b|$)", "tick")
.replaceAll("(\\b|^)\\\\\\((.*)\\\\\\)(\\b|$)", "backslashparen")
.replaceAll("\\*", "%"); // am I matching stars wrong?
return processed;
}
public void test() {
String example = "_Text_\n" +
"*text*\n" +
"~Text~\n" +
"`Text`\n" +
"_Text_\n" + // is it only matching the first one?
"``` Text ```\n" +
"\\(Text\\)\n" +
"~Text~\n";
System.out.println(process(example));
}
我希望所有的行都匹配并被替换,但只有第一行匹配。我想知道这是因为它是第一行,所以我抄在中间,它都匹配。然后我想我可能错过了一些匹配特殊字符的东西,所以我添加了剪报以匹配星号,并用百分号替换,结果成功了。我得到的结果如下:
underscore
%text%
~Text~
`Text`
underscore
``` Text ```
\(Text\)
~Text~
你知道我可能遗漏了什么吗
谢谢。如果您正在使用单词边界,则无需交替匹配锚定,因为单词边界也匹配起始和结束位置。这实际上是冗余匹配:
(?:^|\b)
(?:\b|$)
这两者都可以用\b
代替
但是查看您的正则表达式,请注意,只有下划线被视为单词字符,*
,~
,`
不是单词字符,因此不能在这些字符周围使用\b
,而应使用\b
,这与\b
相反
除此之外,还可以做一些改进,比如使用否定字符类而不是贪婪的*
,以及删除不必要的组
代码:
在所有正则表达式前面加上
(?m)
前缀,以启用多行匹配。因此,我使用了您的建议,它按照我的意愿工作,谢谢。但我不明白的是,第一个(强调)在开始和中间的比赛。你能给我指一个参考资料吗?为什么会这样?再次感谢!使用任何边界都没有意义。尝试同时取出^$和\b。不要使用\B因为如果接受a(
shuld acaepta_u
不要被边界控制显然你在正则表达式的细微差别上比我强。谢谢你的帮助!快速提问,问号是什么?不会是多余的吗?(和不会是一样的吗?+?)?(+?
比+
效率稍高,因为匹配程序是惰性的或非贪婪的,如果您不想匹配空字符串,那么+?
将比*?
效率更高
class MyRegex {
public static void main (String[] args) {
String example = "_Text_\n" +
"*text*\n" +
"~Text~\n" +
"`Text`\n" +
"_Text_\n" + // is it only matching the first one?
"``` Text ```\n" +
"\\(Text\\)\n" +
"~Text~\n";
System.out.println(process(example));
}
private static String process(String input) {
String processed = input.replaceAll("\\b_[^_]+_\\b", "underscore")
.replaceAll("\\B\\*[^*]+\\*\\B", "star")
.replaceAll("\\B```.+?```\\B", "backticks")
.replaceAll("\\B~[^~]+~\\B", "tilde")
.replaceAll("\\B`[^`]+`\\B", "tick")
.replaceAll("\\B\\\\\\(.*?\\\\\\)\\B", "backslashparen");
return processed;
}
}