1

ArrayOutOfBoundsException使用时我感到很奇怪replaceFirst

"this is an example string".replaceFirst("(^this )", "$1\\") // throws ArrayOutOfBoundsException
"this is an example string".replaceFirst("(^this )", "$1") // works fine

我正在尝试实现这个字符串:

"this \is an example string"

如果我尝试在替换字符串中放入转义的反斜杠,为什么会收到 ArrayOutOfBoundsException?这发生在Android上,如果它有所作为

这是异常的一个ideone示例。

这是 logcat 异常堆栈跟踪:

java.lang.ArrayIndexOutOfBoundsException: index=14 at java.util.regex.Matcher.appendEvaluated(Matcher.java:149) at java.util.regex.Matcher.appendReplacement(Matcher.java:111) at java.util.regex。 Matcher.replaceFirst(Matcher.java:304) 在 java.lang.String.replaceFirst(String.java:1793)

4

4 回答 4

3

您需要使用此正则表达式:-

"this is an example string".replaceFirst("(^this )", "$1\\\\");

因为\需要双重转义。因此,对于每个\您需要 4 \(最初您需要 2 \,因此提供此信息,以防您以后需要更改它)。

从这个答案中引用几行:-

第二个参数不是regex-string,而是regex-replacement-string,其中反斜杠也有特殊含义(用于转义变量插值的特殊字符$,也用于转义自身)

于 2013-10-01T10:55:07.577 回答
2
"this is an example string".replaceFirst("(^this )", "$1\\")

在上面的代码中,\\实际上只是一个单一的\(第一个反斜杠用于转义第二个反斜杠,因为 Strings 中的反斜杠用于转义其他内容,本身并不意味着任何东西)。

但!在正则表达式中,单个反斜杠本身用于转义目的,因此需要再次转义。因此,如果您需要在 Java 中的正则表达式字符串中使用文字反斜杠,则需要编写四个反斜杠"\\\\"

于 2013-10-01T10:59:58.723 回答
1

尝试:

"this is an example string".replaceFirst("(^this )", "$1\\\\");

输出:

this \is an example string

String 上的replaceFirstlikereplaceAll函数执行正则表达式,您必须首先转义,\因为它是文字(yielding \\),然后因为正则表达式(yielding \\\\)而再次转义。

于 2013-10-01T10:55:23.937 回答
1

你会需要:

"this is an example string".replaceFirst("(^this )", "$1\\\\");

因为正则表达式需要双重转义。

PS:即使替换的字符串不是真正的正则表达式,但由于使用了 if 分组变量等$1$2它仍然由正则表达式引擎处理,因此需要双重转义。

**相反,如果您想避免使用正则表达式,则只需使用Sring#replace(String n, String r)

"this is an example string".replace("this ", "this \\")

显然这里没有涉及正则表达式,因此只有一次转义就足够了。

于 2013-10-01T10:55:53.893 回答