Reputation: 19
I have the following code
my @txt = ("Line 1. [foo] bar",
"Line 2. foo bar",
"Line 3. foo [bar]"
);
my $regex = qr/^
Line # Bare word
(\d+)\. # line number
\[ # Open brace
(\w+) # Text in braces
] # close brace
.* # slurp
$
/x;
my $nregex = qr/^\s*Line\s*(\d+)\.\s*\[\s*(\w+)\s*].*$/;
foreach (@txt) {
if ($_ =~ $regex) {
print "Lnum $1 => $2\n";
}
if ($_ =~ $nregex) {
print "N Lnum $1 => $2\n";
}
}
N Lnum 1 => foo
I am expecting both the regexs to be equivalent and capture only the first line of the array. However only $nregex
works!
How can $regex
be fixed so that it also works identically (with the x option)?
Based on the response, updated the regex and it works.
my $regex = qr/^ \s*
Line \s* # Bare word
(\d+)\. \s* # line number
\[ \s* # Open brace
(\w+) \s* # Text in braces
] \s* # close brace
.* # slurp
$
/x;
Upvotes: 1
Views: 141
Reputation:
Your two expressions are NOT the same. You need to have the \s* bits in the first one. The /x allows you to write neatly formatted expressions - with comments as you've noticed. As such, the spaces in the /x version are not considered significant, and will not contribute to any matching activity.
In other words, your /x version is the equivalent of
qr/^Line(\d+)\.\[(\w+)].*$/x
By the way, just having a plain space instead of \s* or \s+ would also fail many times; your sample data contains TWO spaces next to each other in a few places. These two places will not match a single space.
Final tip: when you MUST have at least one space in a certain position, you should use \s+ to enforce at least one space. You can surely figure out where that might be useful in your patterns once you know it is possible.
Upvotes: 4