我正在尝试将转换String
\something\
为String
\\something\\
using replaceAll
,但是我不断遇到各种错误。我认为这是解决方案:
theString.replaceAll("\\", "\\\\");
但这给出了以下异常:
java.util.regex.PatternSyntaxException: Unexpected internal error near index 1
我正在尝试将转换String
\something\
为String
\\something\\
using replaceAll
,但是我不断遇到各种错误。我认为这是解决方案:
theString.replaceAll("\\", "\\\\");
但这给出了以下异常:
java.util.regex.PatternSyntaxException: Unexpected internal error near index 1
Answers:
将该String#replaceAll()
参数解释为正则表达式。该\
是转义字符都 String
和regex
。您需要对正则表达式进行两次转义:
string.replaceAll("\\\\", "\\\\\\\\");
但是您不必为此使用正则表达式,仅是因为您想要逐个字符地进行精确替换,并且这里不需要模式。因此String#replace()
就足够了:
string.replace("\\", "\\\\");
更新:根据注释,您似乎想在JavaScript上下文中使用字符串。您最好使用它StringEscapeUtils#escapeEcmaScript()
来覆盖更多字符。
String#replaceAll()
仍然要使用,则可以使用Matcher#quoteReplacement()引用替换字符串:theString.replaceAll("\\", Matcher.quoteReplacement("\\\\"));
为了避免这种麻烦,您可以使用replace
(使用纯字符串)而不是replaceAll
(使用正则表达式)。您仍然需要转义反斜杠,但不需要用正则表达式所要求的狂放方式。
TLDR:theString = theString.replace("\\", "\\\\");
改用。
replaceAll(target, replacement)
对target
部分使用正则表达式(regex)语法replacement
。
问题是,\
正则表达式中的特殊字符(可用于\d
表示数字)和字符串文字中的特殊字符(可用于"\n"
表示行分隔符或\"
转义通常表示字符串文字结尾的双引号。
在这两种情况下,要创建\
符号,我们都可以通过在符号前面放置其他字符来对其进行转义(使它成为文字,而不是特殊字符)\
(例如"
,通过来对字符串文字进行转义\"
)。
因此,target
代表\
符号的正则表达式将需要按住\\
,而代表此类文本的字符串文字则需要看起来像"\\\\"
。
所以我们逃脱了\
两次:
\\
"\\\\"
(每个\
都以表示"\\"
)。万一replacement
\
也很特别。它允许我们转义$
通过$x
符号的其他特殊字符,允许我们使用与正则表达式匹配并由索引为的捕获组保存的部分数据x
,如"012".replaceAll("(\\d)", "$1$1")
将匹配每个数字,将其放入捕获组1并将$1$1
其替换为两个副本(它将复制它),结果为"001122"
。
同样,要replacement
表示\
文字,我们需要使用其他符号对其进行转义,\
这意味着:
\\
\\
看起来像"\\\\"
但是,因为我们要replacement
保留两个反斜杠,所以我们需要"\\\\\\\\"
(每个反斜杠\
代表一个"\\\\"
)。
所以版本replaceAll
可以看起来像
replaceAll("\\\\", "\\\\\\\\");
做出来的生活更轻松Java提供的工具来自动跳脱文本target
和replacement
零件。所以现在我们只关注字符串,而忽略正则表达式语法:
replaceAll(Pattern.quote(target), Matcher.quoteReplacement(replacement))
在我们的情况下看起来像
replaceAll(Pattern.quote("\\"), Matcher.quoteReplacement("\\\\"))
如果我们真的不需要正则表达式语法支持,那就不要介入replaceAll
。相反,让我们使用replace
。两种方法都将替换all target
,但是replace
不涉及正则表达式语法。所以你可以简单地写
theString = theString.replace("\\", "\\\\");
您需要在第一个参数中转义(转义的)反斜杠,因为它是一个正则表达式。替换(第二个参数-参见Matcher#replaceAll(String))也具有反斜杠的特殊含义,因此您必须将其替换为:
theString.replaceAll("\\\\", "\\\\\\\\");