use strict; use warnings; use Data::Dumper::Concise; my $string = "aacbbbcac"; my $re = '((a+)?(b+)?(c))*'; # transform '(x+)?' to '(x*)' assuming 'x' is monolithic $re =~ s/\Q+)?/*)/g; print "re = $re\n"; my $re1 = qr/$re/; if ($string =~ $re1) { my @something; foreach (0..$#-) { if(defined($-[$_])) { my $substring = substr($string, $-[$_], $+[$_] - $-[$_]); # ${$_} also works, except where $_ = 0 no strict 'refs'; print "\$substring = $substring = ${$_}\n"; # transform '' to undef $substring = undef if($substring eq ''); # assert: $substring is now as specified by # Standard ECMA-262, 5.1 Edition / June 2011 # Section 15.10.2.5 Note 3 printf "Group %d: <%s>\n", $_, $substring // ''; $something[$_] = $substring; } } print Dumper(\@something); } #### re = ((a*)(b*)(c))* $substring = aacbbbcac = test.pl Group 0: $substring = ac = ac Group 1: $substring = a = a Group 2: $substring = = Group 3: <> $substring = c = c Group 4: [ "aacbbbcac", "ac", "a", undef, "c" ]