Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Regex with no leading dot and maximum one leading zero

How can I write a regular expression that matches a string with the following properties?:

  1. Contains numbers as well as only dot which is decimal separator (But dot is not necessary which means it can be 123 or 123.4 or 123.56).
  2. No leading dot (Not .12).
  3. Leading zero can be written only if it is followed by a dot (can not be like 000.12, only 0.12).
  4. Have only 2 decimal places.
like image 951
Muhammadjon Avatar asked Dec 24 '22 06:12

Muhammadjon


2 Answers

To the left of the decimal point you want a number (1 or more digits) that doesn't start with a zero:

[1-9][0-9]*

Or it can be just a zero:

0|[1-9][0-9]*

The value may have a decimal point and 1-2 digits after the decimal point:

\.[0-9]{1,2}

Left side is required. Decimal point and fractional digits are optional:

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

The first non-capturing group is needed to limit the scope of the | pattern. The second non-capturing group is needed to make combined "decimal point and fractional digit" pattern optional.

Note that this will allow trailing zeroes, e.g. 100.00


Depending on preference, [0-9] can also be written as \d. I'd normally use \d, but since regex also has [1-9], I liked [0-9] better here as I felt it helped clarify the difference.

Depending on how regex is used, you may need to add the ^ begin / $ end anchors. They are needed when using find(), and are not needed when using matches() but don't hurt:

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

like image 81
Andreas Avatar answered Jan 05 '23 02:01

Andreas


Using negative look-ahead to ensure the string doesn't start with zero and another digit (but can be just zero, or zero followed by a dot)

^(?!0\d)\d+(?:\.\d{1,2})?$

Explanation and sample: https://regex101.com/r/7ymqcn/1

P.S. Also more efficient than Andreas' answer (takes fewer steps to match)

like image 39
Actine Avatar answered Jan 05 '23 01:01

Actine