Reputation: 171
I have this sample code
#!/usr/bin/perl
use strict;
use warnings;
my $string = "Dear Brother,fgfgfg Test Test2 Soon trthggh";
if ($string =~ /(expr1|expr2|dear.{0,6}(brother|friend)|Soon)/i){print "$1";}
$1 will display the match which is "Dear Brother". Is there a way to get the full regepx who match this string?
In this case
dear.{0,6}(brother|friend)
It is possible to do that?
Upvotes: 2
Views: 132
Reputation: 2121
Maybe you could use this approach:
my $part2 = "(brother|friend)";
my $part1 = "(expr1|expr2|dear.{0,6}$part2|Soon)";
my $string = "Dear Brother,fgfgfg Test Test2 Soon trthggh";
if ($string =~ /$part1/i){print "$part1";}
I don't know any more automated way. Maybe you have to hack into a regex engine, not using Perl directly.
Upvotes: -1
Reputation: 3925
If you are creating the regex using a program anyway, it's easy to inject the appropriate (?<...>)
sequences and then just look which one(s) matched afterwards. Adapting the program you posted as first attempt:
#!/usr/bin/perl
use strict;
use warnings;
my $string = "Dear Brother, fgfgfg Test Test2 Soon trthggh";
my @regexarray = (qr/expr1/, qr/expr2/, qr/dear.{0,6}(brother|friend)/i, qr/Soon/, qr/out.php\?s=(7644|4206|6571|4205)/);
my $i= 0;
my $regexstring = join "|", map {
my $groupname= sprintf 'group_%d', $i++;
qr/(?<$groupname>$_)/i
} @regexarray;
if ($string =~ /($regexstring)/i){
my $match = $1;
print "Found <$1>\n";
print "Matched via ";
(my $found) = keys %+;
print "$found => $+{$found}\n" for keys %+;
$found =~ /(\d+)$/
or die "Invalid group name '$found'";
my $index = $1;
print "Matched via /$regexarray[ $index ]/\n";
}
I've switched the strings to regular expressions above to make quoting and case-insensitivity easier.
Found <Dear Brother>
Matched via group_2 => Dear Brother
Matched via /(?^i:dear.{0,6}(brother|friend))/
Upvotes: 5
Reputation: 171
I have this working solution. But on too many expressions, I think the loop may slow down the script. Other, better ideas are welcome, but please stop telling me about $1 or $&.
#!/usr/bin/perl
use strict;
use warnings;
my $string = "Dear Brother, fgfgfg Test Test2 Soon trthggh";
my $regexstring = "expr1|expr2|dear.{0,6}(brother|friend)|Soon|out.php\?s=(7644|4206|6571|4205)";
my @regexarray = ("expr1", "expr2", "dear.{0,6}(brother|friend)", "Soon", "out.php\?s=(7644|4206|6571|4205)");
if ($string =~ /($regexstring)/i){
my $match = $1;
for my $expr (@regexarray){
print "$expr\n" if ($match =~ /($expr)/i);
}
}
Upvotes: 2