regular expression and escaping
Sorry if this has been asked, my search brought up many off topic posts.
I'm trying to convert wildcards from a user defined search string (wildcard is "*") to PostgreSQL like wildcard "%".
I'd like to handle escaping so that "%" => "\%"
and "\*" => "*"
I know I could replace \*
with something else prior to replacing *
and then swap it back, but I'd prefer not to and instead only convert *
using a pattern that selects it when not proceeded by \
.
String convertWildcard(String like)
{
like = like.replaceAll("%", "\\%");
like = like.replaceAll("\\*", "%");
return like;
}
Assert.assertEquals("%", convertWildcard("*"));
Assert.assertEquals("\\%", convertWildcard("%"));
Assert.assertEquals("*", convertWildcard("\\*")); // FAIL
Assert.assertEquals("a%b", convertWildcard("a*b"));
Assert.assertEquals("a\\%b", convertWildcard("a%b"));
Assert.assertEquals("a*b", convertWildcard("a\\*b")); // FAIL
Ideas welcome.
EDIT
To clarify,
I want a method that makes 1 or more String.replaceAll
calls to convert a st开发者_如何学JAVAring so that
- occurrences of
%
become\%
, - occurrences of
*
become%
and - occurrences of
\*
become*
.
The best answer will use the least calls to String.replaceAll
.
You need what is called "Negative Lookbehind". To select all %
not preceded by \
:
(?<!\\)%
(pure regex expression)
to use it in Java you need to add some masking:
string.replaceAll("(?<!\\\\)%", "*");
Note also that you aren't escaping your backslashes enough in some of your assert tests. See the section marked "Regular Expressions, Literal Strings and Backslashes" in http://www.regular-expressions.info/java.html
精彩评论