Home > Software design >  Regex expression for numbers and leading zeros just with a dot and decimal
Regex expression for numbers and leading zeros just with a dot and decimal

Time:02-04

I'm trying to find a regex for numeric inputs. We can receive a leading 0 just if we add a dot for adding 1 or 2 decimal numbers. And of course just accept numbers.

These are the scenarios that we can accept:

0.01 
1.1
1.02
120.01

We can't accept these values

0023
0100
.01
.12

Which regex is the best option for these cases?

Until now we try we the following regex for accepting just number and dots

[A-Za-z,]

And also we try with the following ones:

^[ -]?[0-9]{1,3}(?:[0-9]*(?:[.,][0-9]{1})?|(?:,[0-9]{3})*(?:\.[0-9]{1,2})?|(?:\.[0-9]{3})*(?:,[0-9]{1,2})?)$

"/^[-]?[$]\d{1,3}(?:,?\d{3})*\.\d{2}$/"

"/(^(\d{1})\.{0,1}([0-9]){0,2}$)|(^([1-9])\d{0,2}(\,\d{0,3})$)/g"

(?:0|[1-9][0-9]*)(?:\.[0-9]{1,2})?

And the next one for deleting the leading zeros but it didn't work for 0.10 cases

^0

CodePudding user response:

If a negative lookahead is supported, you can exclude matches that start with a zero and have no decimal part.

^(?!0\d*$)\d (?:\.\d{1,2})?$
  • ^ Start of string
  • (?!0 \d*$) Negative lookahead, assert not a zero followed by optional digits at the right
  • \d Match 1 digits
  • (?:\.\d{1,2})? Match an optional decimal part with 1 or 2 digits
  • $ End of string

Regex demo

CodePudding user response:

I would go with ^(0|[1-9]\d*|(0|[1-9]\d*)\.\d )$

You can test here: https://regex101.com/r/oNMgR9/1

Explanation

  • ^ means : match the beginning of the string (or line if the m flag is enabled).
  • $ means : match the end of the string (or line if the m flag is enabled).
  • (a|b) means match "a" or match "b" so I'll use this to match either "0" alone or any number not starting with a "0". It's the syntax for a logical or.
  • . alone is used to match any char. So you have to escape it if you want to match the dot character. This is why I wrote 0\. instead of 0..
  • [ ] is used to list some characters you want to match. It can be a range if you use the - char, so [1-9] means any digit char from "1" to "9".
  • \d is to match a digit. It's totally equivalent to [0-9].
  • * means : match the preceding pattern 0 or many times, so \d* means that it will match 0 or many times a digit, so it will match "8" or "465" or "09" but also an empty string "". If you want to match the preceding pattern at least once or many times then you use instead of *. So \d won't match an empty string "" but \d* would match it.

A) Just a number not starting with 0

[1-9]\d* will match any digit from 1 to 9 and then optionnaly followed by other digits. This will match numbers without a decimal point.

B) Just 0

0 alone is a possibility. This is because the case above isn't covering it.

B) A number with decimals

(0|[1-9]\d*)\.\d will match either a "0" alone or a number not starting by "0" and then followed by a point and some other digits (which have to be present because we don't want to match "45." without the numbers behind the dot).

Better alternative

The solution from @TheFourthBird is a bit cleaner with the use of a negative lookahead. It's just a bit different to understand. And he read the question completely: You wanted 1 or 2 digits after the decimal. I forgot about that, so, effectively, \d should be replaced by \d{1,2} as you don't want more than 2 digits.

CodePudding user response:

You can use

^(?![0.] $)(?:[1-9]\d*|0)(?:\.\d{1,2})?$

See the regex demo.

Details:

  • ^ - start of string
  • (?![0.] $) - fail the match if there are just zeros or dots till end of string
  • (?:[1-9]\d*|0) - either a non-zero digit followed with any zero or more digits or a zero
  • (?:\.\d{1,2})? - optionally followed with a sequence of a . and one or two digits
  • $ - end of string.
  •  Tags:  
  • Related