Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to capture every match in a global regex substitution?

I realize it is possible to achieve this with a slight workaround, but I am hoping there is a simpler way (since I often make use of this type of expression).

Given the example string:

my $str = "An example: sentence!*"

A regex can be used to match each punctuation mark and capture them in an array. Thereafter, I can simply repeat the regex and replace the matches as in the following code:

push (@matches, $1), while ($str =~ /([\*\!:;])/);
$str =~ s/([\*\!:;])//g;

Would it be possible to combine this into a single step in Perl where substitution occurs globally while also keeping tabs on the replaced matches?

like image 538
Ob1Bob Avatar asked Jan 25 '23 01:01

Ob1Bob


2 Answers

You can embed code to run in your regular expression:

my @matches;
my $str = 'An example: sentence!*';
$str =~ s/([\*\!:;])(?{push @matches, $1})//g;

But with a match this simple, I'd just do the captures and substitution separately.

like image 116
ysth Avatar answered Jan 29 '23 08:01

ysth


Yes, it's possible.

my @matches;
$str =~ s/[*!:;]/ push @matches, $&; "" /eg;

However, I'm not convinced that the above is faster or clearer than the following:

my @matches = $str =~ /[*!:;]/g;
$str =~ tr/*!:;//d;
like image 21
ikegami Avatar answered Jan 29 '23 08:01

ikegami