Using variables in regex compare pattern

Any questions involving matching text strings to patterns - the pattern is called a "regular expression."

Moderator: General Moderators

Post Reply
Ginty
Forum Newbie
Posts: 2
Joined: Mon Jan 28, 2008 12:35 pm

Using variables in regex compare pattern

Post by Ginty »

Hi,
Pretty new to this, but couldn't find an answer by searching the forum, so appreciate any help folks can give...

I have a simple pattern that I want to use to check that a string, $entry, contains only a-z and has a length, between a min and a max value:

eregi("^([a-z]{2,16})$", $entry)

However I want to make the min, max values variables as follows:

$min = 2;
$max = 16;

eregi("^([a-z]{$min,$max})$", $entry)

However this doesn't work, presumably there is some syntax to tell php that that $min and $max should be treated as variables and not part of the regex pattern, but so far I can't work out what it is.

Can you help?

Cheers,
Ginty
User avatar
Chalks
Forum Contributor
Posts: 447
Joined: Thu Jul 12, 2007 7:55 am
Location: Indiana

Re: Using variables in regex compare pattern

Post by Chalks »

Ginty wrote:eregi("^([a-z]{$min,$max})$", $entry)

However this doesn't work, presumably there is some syntax to tell php that that $min and $max should be treated as variables and not part of the regex pattern, but so far I can't work out what it is.
Try this:

Code: Select all

$pattern = "^([a-z]{" . $min . "," . $max . "})$";
eregi($pattern, $entry);
 
Ginty
Forum Newbie
Posts: 2
Joined: Mon Jan 28, 2008 12:35 pm

Re: Using variables in regex compare pattern

Post by Ginty »

Yeah thanks man that works, although I couldn't work out why you have to use the concatenate operator and not just stick it all in double quotes.

Finally narrowed it down to the fact that it doesn't like to see "{$" together within the double quotes - must mean something I guess, anyone know what?

So I can get away with this:

Code: Select all

"^([a-z]{"."$min,$max})$"
Thanks again for your help.
User avatar
Chris Corbyn
Breakbeat Nuttzer
Posts: 13098
Joined: Wed Mar 24, 2004 7:57 am
Location: Melbourne, Australia

Re: Using variables in regex compare pattern

Post by Chris Corbyn »

You're using double quotes so you should really have a backslash infront of that last dollar sign.

The reason it didn't work your way is because {$var} have a special meaning in PHP. It treats the entire bit between the curly braces as a variable.

i.e. these are the same:

Code: Select all

$bar = "doo";
 
$str = "foo $bar";
 
$str = "foo {$bar}";
User avatar
Ollie Saunders
DevNet Master
Posts: 3179
Joined: Tue May 24, 2005 6:01 pm
Location: UK

Re: Using variables in regex compare pattern

Post by Ollie Saunders »

Chris Corbyn wrote:The reason it didn't work your way is because {$var} have a special meaning in PHP. It treats the entire bit between the curly braces as a variable.

Code: Select all

$pattern = "^([a-z]\{$min,$max})$"
This works.

Looks strange though, I will admit. I'd be tempted to use single quotes and the concat op for this one.
User avatar
GeertDD
Forum Contributor
Posts: 274
Joined: Sun Oct 22, 2006 1:47 am
Location: Belgium

Re: Using variables in regex compare pattern

Post by GeertDD »

Moral of the story: always always always use singles quotes around your regexes.

Double quotes do all kinds of weird stuff and you don't want to add another layer of complexity to your regex readability. My $0.02.
User avatar
Ollie Saunders
DevNet Master
Posts: 3179
Joined: Tue May 24, 2005 6:01 pm
Location: UK

Re: Using variables in regex compare pattern

Post by Ollie Saunders »

I've always subscribed to the idea that unless you're using the variable substitution or escaping features of double-quotes you should use single quotes, plus case by case judgement on what's clearest. This means I use single quotes a little more often. Here one example:

Code: Select all

 
$forename = preg_quote($forename, '~');
$surname = preg_quote($surname, '~');
 
// single
$pattern = '~' . $forename . '\s+' . $surname . '~i';
// double
$pattern = "~$forename\s+$surname~i";
Double is clearly better here.
User avatar
GeertDD
Forum Contributor
Posts: 274
Joined: Sun Oct 22, 2006 1:47 am
Location: Belgium

Re: Using variables in regex compare pattern

Post by GeertDD »

ole wrote:

Code: Select all

// single
$pattern = '~'.$forename.'\s+'.$surname.'~i';
// double
$pattern = "~$forename\s+$surname~i";
Double is clearly better here.
I disagree. The single quoted pattern is way easier to read. When I see a regex pattern and I see a $ inside it, first thought that comes up is whether it matches the end of the string or the end of the line. Oh no, it must be a variable here, hmm... The variables are visually pulled out by color coding as well. Also, what if you need to update this pattern later on and allow for alphanumeric characters before or after the vars? How will PHP know then where the variable name stops? Well, let's add some braces around them, yuck. In the other case you could go reconvert the whole thing to single quotes, of course.

Anyway, I'm just saying that I find single quotes to work much more convenient when dealing with regex patterns. Personal opinion.
Post Reply