I'm trying to determine whether or not a expression passed into my Expressions class has an operator. Either +-*/^ for add, subtract, multiply, divide, and exponent respectively.
What is wrong with this code?
private static boolean hasOperator(String expression)
{
return expression.matches("[\+-\*/\^]+");
}
I thought that I had the special characters escaped properly but I keep getting the error: "illegal escape character" when trying to compile.
Thanks for your help.
Don't escape what needs not to be escaped:
return expression.matches("[-+*/^]+");
should work just fine. Most regex metacharacters (., (, ), +, *, etc.) lose their special meaning when used in a character class. The ones you need to pay attention to are [, -, ^, and ]. And for the last three, you can strategically place in them char class so they don't take their special meaning:
^ can be placed anywhere except right after the opening bracket: [a^]
- can be placed right after the opening bracket or right before the closing bracket: [-a] or [a-]
] can be placed right after the opening bracket: []a]
But for future reference, if you need to include a backslash as an escape character in a regex string, you'll need to escape it twice, eg:
"\\(.*?\\)" // match something inside parentheses
So to match a literal backslash, you'd need four of them:
"hello\\\\world" // this regex matches hello\world
Another note: String.matches() will try to match the entire string against the pattern, so unless your string consists of just a bunch of operators, you'll need to use use something like .matches(".*[-+*/^].*"); instead (or use Matcher.find())
Related
I want to check if a String contains a } with any character in front of it except \.
As far as I know I can use . as a metacharacter in aString.contains(...) to allow any character at that position but I don’t know how to create something like a blacklist: aString.contains(“.(except ‘\‘)}“Is that possible without creating an own method?
You need regex (well technically you don't need regex, but it's the best way):
if (aString.matches(".*(?<!\\\\)}.*"))
This regex says the string should be made up as follows
.* zero or more of any character
(?<!\\\\) the previous char is not a backslash
} a curly right bracket
.* zero or more of any character
This also works for the edge case of the first char being the curly bracket.
See live demo.
I'm trying to test if a String ends with EXACTLY two digits after a dot in Java using a Regular Expression. How can achieve this?
Something like "500.23" should return true, while "50.3" or "50" should return false.
I tried things like "500.00".matches("/^[0-9]{2}$/") but it returns false.
Here is a RegEx that might help you:
^\d+\.\d{2,2}$
it may neither be perfect nor the most efficient, but it should lead you in the right direction.
^ says that the expression should start here
\d looks for any digit
+ says, that the leading \d can appear as often as necessary (1–infinity)
\. means you are expecting a dot(.) at one point
\d{2,2} thats the trick: it says you want 2 and exactly 2 digits (not less not more)
$ tells you that the expression ends there (after the 2 digits)
in Java the \ needs to be escaped so it would be:
^\\d*\\.\\d{2,2}$
Edit
if you don't need digits before the dot (.) or if you really don't care what comes before the dot, then you can replace the first \d+ by a .* as in Bohemians answer. The (non escaped) dot means that the expression can contain any character (not only digets). Then even the leading ^ might no longer be necessary.
\\.*\\.\\d{2,2}$
use this regex
String s="987234.42";
if(Pattern.matches("^\\d+(\\.\\d{2})$", s)){ // string must start with digit followed by .(dot) then exactly two digit.
....
}
Firstly, forward slashes are no part of regular expressions whatsoever. They are however used by some languages to delimit regular expressions - but not java, so don't use them.
Secondly, in java matches() must match the whole string to return true (so ^ and $ are implied in the regex).
Try this:
if (str.matches(".*\\.\\d\\d"))
// it ends with dot then 2 digits
Note that in java a bash slash in a regex requires escaping by a further back slash in a string literal.
So, I have this semi-complex regex that is searching for all text in between two strings, then replacing it.
My search regex for this is:
(jump *[A-Z].*)(?:[^])*?([A-Z].*:)
This gives an Unclosed Character Class on the final closing bracket, which I have been struggling to solve. The regex seems to work as intended on RegexR (http://regexr.com/?38k63)
Could anyone provide some help or insight?
Thanks in advance.
The error is at here:
(jump *[A-Z].*)(?:[^])*?([A-Z].*:)
^
In character class ^ is still a special character. It usually negates other characters when you place there. So escape it with \\ in Java.
Different regex engines will treat [^] differently. Some will assume that it's the beginning of a negative character class excluding ] and any characters up to the next ] in the pattern, (e.g. [^][] will match anything except ] and [). Other engines will treat as a empty negative character class (which will match anything). This is why some regex engines will work, and others report it as an error.
If you meant for it to match a literal ^ character, you'll have to escape it like this:
(jump *[A-Z].*)(?:[\^])*?([A-Z].*:)
Or better yet, just remove it from the character class (you'll still have to escape it because ^ has special meaning outside of a character class, too):
(jump *[A-Z].*)(?:\^)*?([A-Z].*:)
Or if you meant for it to match everything up to the next [A-Z].*:, try a character class like this:
(jump *[A-Z].*)(?:[\s\S])*?([A-Z].*:)
And of course, because this is Java, don't forget that you'll need to escape the all the \ characters in any string literals.
Problem seems here in use of [^]:
(jump *[A-Z].*)(?:[^])*?([A-Z].*:)
^
-------------------|
Try this regex instead:
(jump *[A-Z].*)[\\s\\S]*?([A-Z].*:)
OR this:
(?s)(jump *[A-Z].*).*?([A-Z].*:)
Here is the error:
Exception in thread "main" java.util.regex.PatternSyntaxException: Unclosed character class near index 3
], [
^
at java.util.regex.Pattern.error(Pattern.java:1924)
at java.util.regex.Pattern.clazz(Pattern.java:2493)
at java.util.regex.Pattern.sequence(Pattern.java:2030)
at java.util.regex.Pattern.expr(Pattern.java:1964)
at java.util.regex.Pattern.compile(Pattern.java:1665)
at java.util.regex.Pattern.<init>(Pattern.java:1337)
at java.util.regex.Pattern.compile(Pattern.java:1022)
at java.lang.String.split(String.java:2313)
at java.lang.String.split(String.java:2355)
at testJunior2013.J2.main(J2.java:31)
This is the area of the code that is causing the issues.
String[][] split = new String[1][rows];
split[0] = (Arrays.deepToString(array2d)).split("], ["); //split at the end of an array row
What does this error mean and what needs to be done to fix the code above?
TL;DR
You want:
.split("\\], \\[")`
Escape each square bracket twice — once for each context in which you need to strip them from their special meaning: within a Regular Expression first, and within a Java String secondly.
Consider using Pattern#quote when you need your entire pattern to be interpreted literally.
Explanation
String#split works with a Regular Expression but [ and ] are not standard characters, regex-wise: they have a special meaning in that context.
In order to strip them from their special meaning and simply match actual square brackets, they need to be escaped, which is done by preceding each with a backslash — that is, using \[ and \].
However, in a Java String, \ is not a standard character either, and needs to be escaped as well.
Thus, just to split on [, the String used is "\\[" and you are trying to obtain:
.split("\\], \\[")
A sensible alternative
However, in this case, you're not just semantically escaping a few specific characters in a Regular Expression, but actually wishing that your entire pattern be interpreted literally: there's a method to do just that 🙂
Pattern#quote is used to signify that the:
Metacharacters [...] in your pattern will be given no special meaning.
(from the Javadoc linked above)
I recommend, in this case, that you use the following, more sensible and readable:
.split(Pattern.quote("], ["))
Split receives a regex and [, ] characters have meaning in regex, so you should escape them with \\[ and \\].
The way you are currently doing it, the parser finds a ] without a preceding [ so it throws that error.
String.split() takes a regular expression, not a normal string as an argument. In a regular expression, ] and [ are special characters, which need to be preceded by backslashes to be taken literally. Use .split("\\], \\["). (the double backslashes tell Java to interpret the string as "\], \[").
.split("], [")
^---start of char class
end----?
Change it to
.split("], \[")
^---escape the [
Try to use it
String stringToSplit = "8579.0,753.34,796.94,\"[784.2389999999999,784.34]\",\"[-4.335912230999999, -4.3603307895,4.0407909059, 4.08669583455]\",[],[],[],0.1744,14.4,3.5527136788e-15,0.330667850653,0.225286999939,Near_Crash";
String [] arraySplitted = stringToSplit.replaceAll("\"","").replaceAll("\\[","").replaceAll("\\]","").trim().split(",");
I am new to regex. I have this regex:
\[(.*[^(\]|\[)].*)\]
Basically it should take this:
[[a][b][[c]]]
And be able to replace with:
[dd[d]]
abc, d are unrelated. Needless to say the regex bit isn't working. it replaces the entire string with "d" in this case.
Any explanation or aid would be great!
EDIT:
I tried another regex,
\[([^\]]{0})\]
This one worked for the case where brackets contain no inner brackets and nothing else inside. But it doesn't work for the described case.
You need to know that . dot is special character which represents "any character beside new line mark" and * is greedy so it will try to find maximal match.
In your regex \[(.*[^(\]|\[)].*)\] first .* will represent maximal set of characters between [ and [^(\]|\[)].*)\]] and this part can be understood as non [ or ] character, optional other characters .* and finally ]. So this regex will match your entire input.
To get rid of that problem remove both .* from your regex. Also you don't need to use | or ( ) inside [^...].
System.out.println("[[a][b][[c]]]".replaceAll("\\[[^\\]\\[]\\]", "d"));
Output: [dd[d]]
\[(\[a\])(\[b\])\[(\[c\])\]\]
If you need to double backslashes in the current context (such as you are placing it in a "" style string):
\\[(\\[a\\])(\\[b\\])\\[(\\[c\\])\\]\\]
An example replacement for a, b and c is [^\]]*, or if you need to escape backslashes [^\\]]*.
Now you can replace capture one, capture two and capture three each with d.
If the string you are replacing in is not exactly of that format, then you want to do a global replacement with
(\[a\])
replacing a,
(\[[^\]]*\])
doubling backslashes,
(\\[[^\\]]*\\])
Try this:
System.out.println("[[a][b][[c]]]".replaceAll("\\[[^]\\[]]", "d"));
if a,b,c are in real world more than one character, use this:
System.out.println("[[a][b][[c]]]".replaceAll("\\[[^]\\[]++]", "d"));
The idea is to use a character class that contains all characters but [ and ]. The class is: [^]\\[] and other square brackets in the pattern are literals.
Note that a literal closing square bracket don't need to be escaped at the first position in a character class and outside a character class.