Beefy Boxes and Bandwidth Generously Provided by pair Networks
The stupid question is the question not asked
 
PerlMonks  

regex variables

by Angel (Friar)
on Nov 18, 2002 at 20:06 UTC ( [id://213869]=perlquestion: print w/replies, xml ) Need Help??

Angel has asked for the wisdom of the Perl Monks concerning the following question:

I asked a few days ago about basic regex, I have realized that what I could do is since I have to perform similar regex on about 40+ input variables if I could make the regex string a variable and store it in a hash I sould make my system much more efficent.
#my idea %character_tests{ "var1" , "^0-9", "var2" , "^A-Za-z0-9\." ); #object update nethod # ARGS: variable name , variable value # RETURNS: 1 if sucessful, undef if not # sets error vars not described here sub update( $ ) { if( $_[0] =~ /$character_tests{ $_[0] )/ ) { &set_error_type = "illegal characters"; } else { $self->{var1} = $_[0]; } }
Is this good programming stype or am I shooting my self in the foot for later?

Replies are listed 'Best First'.
Re: regex variables
by sauoq (Abbot) on Nov 18, 2002 at 20:35 UTC

    It's a fine technique to use but you need to be a little careful about how you use it. Using double quotes to quote the pattern is a sure way to shoot yourself in the foot. It is better to use qr() for this.

    Take your example, for example...

    %character_tests{ "var1" , "^0-9", "var2" , "^A-Za-z0-9\." );
    The first problem is that your hash initialization is all messed up and you have a typo too. We'll ignore that for the time being. The second problem with that is that you almost surely want character classes. I.e. "^0-9" will match a string that starts with the literal string "0-9". You mean probably mean either "[^0-9]" (anything that isn't a digit, better represented as \D) or "^[0-9]" (anything that starts with a digit, better represented by '^\d'. I'm going to assume its the latter you really wanted. See how I used single quotes around it? That's because if I used double quotes the \d would have looked like an escaped "d" which is simply a literal "d". So, the resulting regex would have matched anything that started with a "d" instead of a digit. That's why you shouldn't use double quotes.

    As I said, the qr() quoting operator is provided for just this sort of thing. You could write the snippet above as...

    %character_tests = ( var1 => qr/^0-9/, var2 => qr/^A-Za-z0-9\./ );
    First, notice the assignment? That's required to initialize the hash. Notice also that I use parens. Braces are for hash refs. Don't worry about them right now. You really should pick more descriptive keys but those will suffice for now.

    You would use such a regex like this:

    $somestring =~ $character_tests{var1};
    You can also use them inside another regex.
    $somestring =~ /$character_tests{var1}Foo/;
    Read perldoc perlop for more information on qr() and perldoc perlre for more information on regular expressions in general.

    -sauoq
    "My two cents aren't worth a dime.";
    
Re: regex variables
by Thelonius (Priest) on Nov 18, 2002 at 21:08 UTC
    In addition to what sauoq says, please note that for character classes you need to include square brackets. And your update routine is wrong. Presumably you want something like:
    %character_tests = ( var1 => qr/[^0-9]/, var2 => qr/[^A-Za-z0-9\.]/ ); sub update( $ ) { if( $_[1] =~ /$character_tests{ $_[0] )/ ) { &set_error_type = "illegal characters"; return undef; } else { $self->{$_[0]} = $_[1]; return 1; # to match your spec } }
    This will let you assign to var1 only if the value does not contain a digit.
Re: regex variables
by Courage (Parson) on Nov 18, 2002 at 20:32 UTC
    you could just use regular expressions as hash values using qr// syntax, and then test your variable for match.

    Better yet, your current code sample makes me think that you should think about rethinking your code design.

    Best wishes,
    Courage, the Cowardly Dog

Re: regex variables
by John M. Dlugosz (Monsignor) on Nov 18, 2002 at 21:48 UTC
    Poetry mode?
    (my $self=shift)->shoot('foot') for (@later);

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://213869]
Approved by diotalevi
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others rifling through the Monastery: (6)
As of 2024-04-19 11:16 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found