Validating Money Strings

Ok, we can now use what we’ve learned to work on something useful: a regular expression

to check user input of an amount of money. A quantity of money can be written in four ways

we can consider acceptable: “10000.00” and “10,000.00”, and, without

the cents, “10000” and “10,000”. Let’s begin with:

to check user input of an amount of money. A quantity of money can be written in four ways

we can consider acceptable: “10000.00” and “10,000.00”, and, without

the cents, “10000” and “10,000”. Let’s begin with:

`^[1-9][0-9]*$`

That validates any number that doesn’t start with a 0. But that also means the string

“0” doesn’t pass the test. Here’s a solution:

“0” doesn’t pass the test. Here’s a solution:

^(0|[1-9][0-9]*)$

“Just a zero OR some number that doesn’t start with a zero.” We may also

allow a minus sign to be placed before the number:

allow a minus sign to be placed before the number:

^(0|-?[1-9][0-9]*)$

That means: “a zero OR a possible minus sign and a number that doesn’t start with

a zero.” Ok, let’s not be so strict and let the user start the number with a zero.

Let’s also drop the minus sign, as we won’t be needing it for the money string. What we

could do is specify an optional decimal fraction part in the number:

a zero.” Ok, let’s not be so strict and let the user start the number with a zero.

Let’s also drop the minus sign, as we won’t be needing it for the money string. What we

could do is specify an optional decimal fraction part in the number:

^[0-9]+(.[0-9]+)?$

It’s implicit in the highlited construct that a period always comes with at least one

digit, as a whole set. So, for instance, “10.” is not validated, whereas

“10” and “10.2” are.

digit, as a whole set. So, for instance, “10.” is not validated, whereas

“10” and “10.2” are.

^[0-9]+(.[0-9]{2})?$

We specified that there must be exactly two decimal places. If you think that’s too

harsh, you can do the following:

harsh, you can do the following:

^[0-9]+(.[0-9]{1,2})?$

That allows the user to write just one number after the period. Now, as for the commas

separating the thousands, we can put in:

separating the thousands, we can put in:

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

“A set of 1 to 3 digits followed by zero or more sets of a comma and three

digits.” Easy enough, isn’t it? But let’s make the commas optional:

digits.” Easy enough, isn’t it? But let’s make the commas optional:

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

That’s it. Don’t forget that the

strings to be accepted also (why?). And don’t forget to escape the backslash for the

function call (common mistake here). Now, once the string is validated, we strip off any

commas with

so we can make math with it.

`'+'`

can be substituted by a `'*'`

if you want emptystrings to be accepted also (why?). And don’t forget to escape the backslash for the

function call (common mistake here). Now, once the string is validated, we strip off any

commas with

` str_replace(",", "", $money)`

and typecast it to **double**so we can make math with it.