Is there Any End of Underscores in Numeric Literals? - java

I just read Enhancements in Java7(
http://docs.oracle.com/javase/7/docs/technotes/guides/language/underscores-literals.html).
In that I see Underscores Numeric Literals and try Like....
int i=9_000; its OK.
But I see rules for that it also allows like...
int i=9____________________________________________________________________________________000;
Is there any end of Underscores?

There's no limit. Why should there be ? On the other hand, the only reason I see to use any number of underscores, is to be able to do fancy stuff like in the following piece of code (created by Joshua Bloch, if I'm not mistaken):
private static final int BOND =
0000_____________0000________0000000000000000__000000000000000000+
00000000_________00000000______000000000000000__0000000000000000000+
000____000_______000____000_____000_______0000__00______0+
000______000_____000______000_____________0000___00______0+
0000______0000___0000______0000___________0000_____0_____0+
0000______0000___0000______0000__________0000___________0+
0000______0000___0000______0000_________0000__0000000000+
0000______0000___0000______0000________0000+
000______000_____000______000________0000+
000____000_______000____000_______00000+
00000000_________00000000_______0000000+
0000_____________0000________000000007;

No, there's no limit. Java allows any amount of underscores although, depending on how your compiler is implemented, you may run into problems for bizarre edge cases like several billion of them :-)
In those places where you can have underscores, the language specification does not limit the quantity. I emphasise "can" there because there are places where they're not allowed, such as before the first digit, after the last, next to the decimal point and so on. But that's a different issue.
However, rather than ask if it's possible, you should instead ask what would be the point of more than one consecutive underscore.
One underscore aids readability by naturally grouping the numbers:
1_000_000
4072_1199_6645_1234 whereas more than one tends to reduce readability:
1_0_0________000_0
4072___________________________11_9_9_6641234

Here is the definition of a decimal literal from the JLS:
DecimalNumeral:
0
NonZeroDigit Digitsopt
NonZeroDigit Underscores Digits
Digits:
Digit
Digit DigitsAndUnderscoresopt Digit
Digit:
0
NonZeroDigit
NonZeroDigit: one of
1 2 3 4 5 6 7 8 9
DigitsAndUnderscores:
DigitOrUnderscore
DigitsAndUnderscores DigitOrUnderscore
DigitOrUnderscore:
Digit
_
Underscores:
_
Underscores _
Notice the recursive definition for Underscores, fun!

No. Here is the document:
http://docs.oracle.com/javase/7/docs/technotes/guides/language/underscores-literals.html
In Java SE 7 and later, any number of underscore characters (_) can
appear anywhere between digits in a numerical literal.

Related

Java - Regex for oracle NUMBER(10,8) field

I have an Oracle column of data type NUMBER(10,8). I need to validate the input data via java regex before the storing the data in tables. As per oracle's data type, valid values include:
10 digits
2 digits . 8 digits
3 digits . 7 digits
4 digits . 6 digits
no digits . 8 digits (is saved in Oracle as 0.12345678 but the input value can be like .12345678)
and so on. Negative values of these cases are also valid.
I can write regex for one case at a time. i.e we can check for 1234567891 with one regex. Then with changes in the range, we can write respective regex for all the possible combinations of the scale.
My sample regex : ^-?\\d{0,2}(?>\\.\\d{1,8})?$ : checks for 2 digits . 8 digits case.
Now I want to know, is there any easier way of checking all such values in one regex? One can always use a '|' operator but then the total number of such OR regex would be equal to the scale part of the data type.
Is there any elegant possible solution? Any pointers, suggestions are welcome!
UPDATE :
After #Andreas pointed out the actual meaning of (10,8), the question does seem to be misguided. Removing the invalid cases from the above mentioned, the valid cases are :
(0/1/2 digits).(0/1/2/../8 digits)
0/1/2 digits
negative cases
You've misunderstood the meaning of NUMBER(10,8):
Specify a fixed-point number using the following form:
NUMBER(p,s)
where:
p is the precision, or the maximum number of significant decimal digits, where the most significant digit is the left-most nonzero digit, and the least significant digit is the right-most known digit. [...]
s is the scale, or the number of digits from the decimal point to the least significant digit. [...]
It means maximum 10 significant decimal digits, with 8 digits from the decimal point, i.e. 2.8 only. The scale is not floating. Sure, you can have fewer on each side of the decimal point, but no mote than 2 on the left and 8 on the right.
Oracle names this a fixed-point number, and it is very distinct from a floating-point number, which uses the same keyword but without limits, i.e. NUMBER.
As for Oracle Database number literal format, the format is:
If you exclude scientific notation, that means a regex of:
^[+-]?(?:\d{1,2}(?:\.\d{0,8})?|\.\d{1,8})$
EDIT
Please note that this answer was provided prior to the OP's update and is no longer correct. I will leave this here in case it helps any future readers, but at the time of writing this edit Andreas' answer seems to be correct.
This may be easier to achieve by simply splitting the string on . and then testing each side's length, but this can still be achieved using regex alone.
See this regex in use here
^(?=[\d.]{1,10}$)(?:\d+(?:\.\d+)?|\.\d{1,8})$
^ Assert position at the start of the line
(?=[\d.]{1,10}$) Positive lookahead to ensure the line has a maximum of 10 characters and is composed of only digits and ..
(?:\d+(?:\.\d+)?|\.\d{1,8}) Match either of the following options
\d+(?:\.\d+)? Match any digit one or more times, optionally followed by a decimal point . and more digits (one or more). You can change \.\d+ to \.\d* to match numbers like 1. that don't have decimal numbers specified.
\.\d{1,8} Match . followed by a digit between 1-8 times. Since the 0 is implied here, it's actually the 9th digit for this number (the dot being the tenth).
$ Assert position at the end of the line
For matching the possibility of + or - at the start of the number, the following may be used.
See regex in use here
^(?=[-+\d.]{1,10}$)(?:[-+]?\d+(?:\.\d+)?|\.\d{1,8}|[+-]\.\d{1,7})$
Regex is a chomsky language of typ-3, which can not calculate something. You can only or-combine all possible formats, which results in a long and unmaintainable regex. So the easiest solution is a functional check.

Is there a wildcard for intergers to use in regex?

I want to know if there is a way to check if a string contains a certain pattern for a regex.
For example:
string.matches("something[0-9]x") would check if the string contains a substring of "something" with any single digit integer following it followed by "x". But lets say if I want to check the same thing, but there is no limit for that int, ie it could be 1000000. Is there like a wildcard for an int that I can use?
Just use modifier + after your character class which match the preceding token one or more time :
string.matches("something[0-9]+x")
Regular expressions work on characters; they have no semantic understanding of those characters. So it doesn't make sense to talk about "integers" here; the best that you can do is to talk about "digits". The number "1" is one digit; "1234" is four.
In a regular expression, you can match one or more of the preceding pattern using "+", so the regex "something[0-9]+x" should do what you want. If you want an upper bound on the number of digits, than you can try something like "something[0-9]{1,5}x"
Yes, simply use *, so in your example string.matches("something[0-9]+x")
It would match a string something followed by any digit from 0 to 9, which have to occur at least one time, so * means zero or more times, while + means it have to occur at least one time but can occur more times if it wants.
If you do [0-9]{n,m} you can specify with m and n in which range it can occur for example:
[0-9]{2,3} will match any digit and it have to occur 2 or 3 times, if you only use one digit in this bracs [0-9]{2} it has to occur at least 2 times.
But at last: simply learn to use google ... there are so many regexp sites with tutorials and stuff.

Password expression is not working as expected

I have a password expression like below.
It has to allow either one small letter, one capital letter, one numeric or one small letter, one capital letter , one special character or one small letter, one capital letter, one numeric, one special character. I joined all the three conditions using | or. It should be min of 8 and max 20 characters. It should allow only specific special characters $##!%. But here it is allowing all the special characters though I mentioned specific set. Thats the main issue. I spent lot time in changing patterns but still the same allowing all special characters. –
I don't understand why its allowing ^ (Marr1234^)?
(((?=.\d)(?=.[a-z])(?=.[A-Z])(?=.[$##!%]))|((?=.[a-z])(?=.[A-Z])(?=.[$##!%]))|((?=.\d)(?=.[a-z])(?=.[A-Z]))).{8,20}
Any ideas
Have you thought about .{8,20} matching your input? This term matches every character (.==every character) 8 up to 20 times... So this would also match the ^-character
Thanks rdmuller for the help. I was able to fix it.
I need to add the range [A-Za-z0-9] and avoid "." like .{8,20}.
Here is the expression I used
^(?=.\d)(?=.[a-z])(?=.*[A-Z])[A-Za-z0-9]{8,20}$

Regex for numbers between 0 and 180 and decimals places in Javacc

So I'm creating a token in JavaCC by using regex.
I'm trying to only allow 3 digit numbers and is only between 0 - 180.
Also, I'm trying to only allow (in a separate token) 2 digit numbers between 0 and 59.9999 (4 decimal places).
I have no idea how to create the regex for these two tokens in JavaCC...
Any help would with an explanation would be awesome thanks :)
For the first case, your pattern needs to allow 1-digit numbers, 2-digit numbers, 3-digit numbers whose first digit is 1 and whose second digit is in the range 0-7, and the special case 180. The regex would look like
[0-9]{1,2}|1[0-7][0-9]|180
(I don't know javacc, so I don't know how this regex would be used, or whether you need something else to prevent something like 1800 from being parsed as a number, or as two numbers. You might need \b on the ends to indicate a word boundary, but I have no idea how javacc works.)
For the second case, the part to the left of the decimal point is either one digit, or two digits where the first digit is in the range 0-5. Your requirements aren't clear, but if the token is required to have a decimal point and one to four digits to the right of the decimal point, the regex would be
([0-9]|[0-5][0-9])\.[0-9]{1,4}
Again, I don't know how javacc handles the word boundaries.
Note that if this were a Java program, I would recommend (in the first case) just parsing it as an integer and comparing it to 0 and 180. Too many questioners try to use regexes to solve every problem, but they are not suited for every problem. Since this is for javacc, it may be a context in which regexes are simple to use and numeric comparisons are not--as I've mentioned, I don't know anything about javacc.

Set minimum and maximum characters in a regular expression

I've written a regular expression that matches any number of letters with any number of single spaces between the letters. I would like that regular expression to also enforce a minimum and maximum number of characters, but I'm not sure how to do that (or if it's possible).
My regular expression is:
[A-Za-z](\s?[A-Za-z])+
I realized it was only matching two sets of letters surrounding a single space, so I modified it slightly to fix that. The original question is still the same though.
Is there a way to enforce a minimum of three characters and a maximum of 30?
Yes
Just like + means one or more you can use {3,30} to match between 3 and 30
For example [a-z]{3,30} matches between 3 and 30 lowercase alphabet letters
From the documentation of the Pattern class
X{n,m} X, at least n but not more than m times
In your case, matching 3-30 letters followed by spaces could be accomplished with:
([a-zA-Z]\s){3,30}
If you require trailing whitespace, if you don't you can use: (2-29 times letter+space, then letter)
([a-zA-Z]\s){2,29}[a-zA-Z]
If you'd like whitespaces to count as characters you need to divide that number by 2 to get
([a-zA-Z]\s){1,14}[a-zA-Z]
You can add \s? to that last one if the trailing whitespace is optional. These were all tested on RegexPlanet
If you'd like the entire string altogether to be between 3 and 30 characters you can use lookaheads adding (?=^.{3,30}$) at the beginning of the RegExp and removing the other size limitations
All that said, in all honestly I'd probably just test the String's .length property. It's more readable.
This is what you are looking for
^[a-zA-Z](\s?[a-zA-Z]){2,29}$
^ is the start of string
$ is the end of string
(\s?[a-zA-Z]){2,29} would match (\s?[a-zA-Z]) 2 to 29 times..
Actually Benjamin's answer will lead to the complete solution to the OP's question.
Using lookaheads it is possible to restrict the total number of characters AND restrict the match to a set combination of letters and (optional) single spaces.
The regex that solves the entire problem would become
(?=^.{3,30}$)^([A-Za-z][\s]?)+$
This will match AAA, A A and also fail to match AA A since there are two consecutive spaces.
I tested this at http://regexpal.com/ and it does the trick.
You should use
[a-zA-Z ]{20}
[For allowed characters]{for limiting of the number of characters}

Categories