By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
435,089 Members | 1,964 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 435,089 IT Pros & Developers. It's quick & easy.

Strange RegExp problem

P: n/a
r
Hello,

It seems delimiters can cause trouble sometimes.

Look at this :

<script type="text/javascript">
function isDigit(s) {
var DECIMAL = '\\.';
var exp = '/(^[+]?0(' + DECIMAL
+'0+)?$)|(^([-+]?[1-9][0-9]*)$)|(^([-+]?((0?|[1-9][0-9]*)' + DECIMAL
+'(0*[1-9][0-9]*)))$)|(^[-+]?[1-9]+[0-9]*' + DECIMAL +'0+$)/';
return RegExp(exp).test(s);
};
document.write(isDigit('123.45') ? '1' : '0');
document.write(isDigit('123') ? '1' : '0');
document.write(isDigit('123.00') ? '1' : '0');
</script>

With / delimiters, third test fails.
With | delimiters, it's ok.

Same behavior with firefox,ie7,safari.

Can someone explain this ?

Thanks.
Oct 14 '08 #1
Share this Question
Share on Google+
4 Replies


P: n/a
r@ph wrote:
var exp = '/(^[+]?0(' + DECIMAL
+'0+)?$)|(^([-+]?[1-9][0-9]*)$)|(^([-+]?((0?|[1-9][0-9]*)' + DECIMAL
+'(0*[1-9][0-9]*)))$)|(^[-+]?[1-9]+[0-9]*' + DECIMAL +'0+$)/';
return RegExp(exp).test(s);
// serve as delimiters for regular expression literals. You don't use
them in strings passed to the RegExp constructor, unless you really want
to match a slash.

--

Martin Honnen
http://JavaScript.FAQTs.com/
Oct 14 '08 #2

P: n/a
r
> var exp = '/(^[+]?0(' + DECIMAL
>+'0+)?$)|(^([-+]?[1-9][0-9]*)$)|(^([-+]?((0?|[1-9][0-9]*)' + DECIMAL
+'(0*[1-9][0-9]*)))$)|(^[-+]?[1-9]+[0-9]*' + DECIMAL +'0+$)/';
return RegExp(exp).test(s);
// serve as delimiters for regular expression literals. You don't use them
in strings passed to the RegExp constructor, unless you really want to
match a slash.

Hi Martin,
Can you explain this a little more please ?
In my sample, why only the 3rd case fails ?
Thanks a lot.
Oct 14 '08 #3

P: n/a
"r@ph" <r-*****************@inrezo.comwrites:
It seems delimiters can cause trouble sometimes.
No doubt. Most things can :)
Look at this :

<script type="text/javascript">
function isDigit(s) {
var DECIMAL = '\\.';
var exp = '/(^[+]?0(' + DECIMAL
+'0+)?$)|(^([-+]?[1-9][0-9]*)$)|(^([-+]?((0?|[1-9][0-9]*)' + DECIMAL
+'(0*[1-9][0-9]*)))$)|(^[-+]?[1-9]+[0-9]*' + DECIMAL +'0+$)/';
ICK. Now I have looked. I need to go wash my eyes. With soap.

Ahem, anyway ...
The "/" at the start and end of "exp" is pretty certainly wrong.

A javascript regexp *literal* is delimited by slashes, e.g.,
/foo|bar/. The corresponding constructor call would be RegExp("foo|bar"),
where the regexp is in a string literal, delimited by the string quotes,
and therefore doesn't need any other delimination ... deliminion ...
something.

The "/"'s above merely cause the first and last alternative of the
regexp to fail because they expect a slash before the start of the
string, or after the end.
return RegExp(exp).test(s);
};
document.write(isDigit('123.45') ? '1' : '0');
document.write(isDigit('123') ? '1' : '0');
document.write(isDigit('123.00') ? '1' : '0');
</script>

With / delimiters, third test fails.
With | delimiters, it's ok.
Where did you put the '|' "delimiters"? In the same palce as the '/'?
Then the first and last alternative would start to work, and you would
also have added two ways of matching the empty substring, meaning that
*all* strings would match. Try isDigit("Arglebargle").
Same behavior with firefox,ie7,safari.
Then it's probably intended behavior.
Can someone explain this ?
Yep, it's what you asked for :)

Stick to regexp literals if possible, they are easier to read,, and
you don't have to escape your backslashes.
var exp = '/(^[+]?0(' + DECIMAL
+'0+)?$)|(^([-+]?[1-9][0-9]*)$)|(^([-+]?((0?|[1-9][0-9]*)' + DECIMAL
+'(0*[1-9][0-9]*)))$)|(^[-+]?[1-9]+[0-9]*' + DECIMAL +'0+$)/';
If I read the regexp correctly, it should match any of:
- An optional plus and a single zero, optionally followed by a decimal
point and one or more zeros.
- An optional sign and a non-zero digit followed by any number of digits.
- An optional sign and either zero or (a non-zero digit followed by any
number of digits), followed by a decimal point and a sequence of digits
containing at least one non-zero digit.
- An optional sign and a non-zero digit followed by any number of digits,
followed by a decimal point and a nonzero number of zeros.

I.e., an optional sign, either a single zero multiple digits not startine
with a zero, and optionally a decimal point and more than one digit -
except you don't allow minus zero.

It might be easier to use two checks:

/^[-+]?(?:0|[1-9]\d+)(?:\.\d+)?$/
AND NOT
/^-0(?:\.0+)$/

If that's not possible, I think the above can also be made a little
shorter (and avoid the DECIMAL constant, unless you do it for
readablilty):
/^(?:\+?0(?:\.0+)?|[-+]?(?:0\.0*[1-9]\d*|[1-9]\d*(?:\.\d+)?))$/

Best of luck.
/L 'likes regexps'
--
Lasse Reichstein Holst Nielsen
DHTML Death Colors: <URL:http://www.infimum.dk/HTML/rasterTriangleDOM.html>
'Faith without judgement merely degrades the spirit divine.'
Oct 14 '08 #4

P: n/a
r
Hello,

Thanks for this complete answer.
A javascript regexp *literal* is delimited by slashes, e.g.,
/foo|bar/. The corresponding constructor call would be RegExp("foo|bar"),
where the regexp is in a string literal, delimited by the string quotes,
and therefore doesn't need any other delimination ... deliminion ...
something.
Understood.
Where did you put the '|' "delimiters"? In the same palce as the '/'?
Then the first and last alternative would start to work, and you would
also have added two ways of matching the empty substring, meaning that
*all* strings would match. Try isDigit("Arglebargle").
Exact. I'm confused :S
This code and my problem come from the tablesorter jquery plugin. I warn the
author now.

Thanks again.
Raph
Oct 14 '08 #5

This discussion thread is closed

Replies have been disabled for this discussion.