tags:

views:

253

answers:

4

I have a regex where the variable $m_strFirstName is next to other identifier characters that aren't part of the variable name:

if($strWholeName =~ m/$m_strFirstName_(+)/) 
....

I'm trying to extract something like:

  • strWholeName is 'bob_jones' or 'bob_smith'
  • m_strFirstName is 'bob'
  • and I want the 'smith' or 'jones' part of the string.
  • if strWholeName is "frank_jones" I want to ignore that, so the if statement would be false

Obviously,

m/$m_strFirstName_(+)/

is not going to work because the regex interpreter won't treat the $m_strname part as I intended, so any ideas?

EDIT: my original question was not clear, updated.

Thanks

+5  A: 

Put braces around your variable name:

if($strname =~ m/${m_strName}_(.+)/)
Josh Kelley
Awesome, that worked! thanks!
cbrulak
Wouldn't that be m/${m_strName}_(.+)/ (missing the dot)
Mathieu Longtin
Using m/\Q${m_strName}\E_(.+)/ should be safer.
Hynek -Pichi- Vychodil
Because you haven't anchored the regex, this will incorrectly match e.g. a $strname of "jeanne_smith" to a $m_strName of "anne".
j_random_hacker
+2  A: 
$foo = "yodeling yoda"
$bar = "ing yo"

if ($foo =~ /\Q$bar\E/)
{
  print "true"
}
I tend to use the \Q...\E because something about breaking up my dollar signs and the identifiers with which they belong rubs me the wrong way.
+1 \Q\E is a good habit to get into for interpolating into regexen at all times. Only omit them if you know that you really want to.
ephemient
+3  A: 

Josh has the right answer, but if you turned on strict and warnings, you could have found it for yourself. Here's (basically) your script as it was originally:

my($strWholeName) = "Bob_Jones";
my($m_strFirstName) = "Bob";

if($strWholeName =~ m/$m_strFirstName_(.+)/) {
    print "Last name is <$1>\n";
}

which resulted in the following:

C:\temp>perl test.pl
Last name is <Bob_Jones>

If you add the following two lines:

use strict;
use warnings;

you get the following output instead:

C:\temp>perl test.pl
Global symbol "$m_strFirstName_" requires explicit package name at test.pl line
7.
Execution of test.pl aborted due to compilation errors.

Add in the braces per Josh's answer and you finally get:

C:\temp>perl test.pl
Last name is <Jones>

Always, always, always use strict and use warnings!

See brian's Guide to Solving Any Perl Problem from Mastering Perl for more nifty tricks.

Joe Casadonte
that's great advice, thanks!
cbrulak
+3  A: 
if ($strWholeName =~ m/^\Q$m_strFirstName\E_(.+)/)

Differences from Josh Kelley's answer:

  1. You must anchor the regex to the start of the string, otherwise e.g. a $strWholeName of "jeanne_smith" will incorrectly match a $m_strFirstName of "anne".
  2. You should surround $m_strFirstName with \Q and \E to quote any strange characters (unless you are absolutely sure they cannot appear -- but why not do it anyway as it is cheap and guarantees safety). Hynek Vychodil mentioned this in a comment on Josh's answer.
j_random_hacker