Perl Regex - Print the matched value
/(\d+$)/;
print $1;
I guess you just want the number 195
. Right?
How about just:
print $string =~ /Total Successful Transactions = (\d+)/;
You rarely actually need to use $1
and friends.
You can use parentheses in regex to capture substrings. The captured groups are stored in $1, $2, and so on. Example:
while (<>) {
if (/Total Successful Transactions = (\d+)/) {
print "$1\n";
}
}
or, somewhat shorter:
while (<>) {
print "$1\n" if /Total Successful Transactions = (\d+)/;
}
You can also make use of the fact that the match operator (//
) in list context returns a list of what was matched by groups:
$\ = '\n'; # Output newline after each print.
while (<>) {
print for /Total Successful Transactions = (\d+)/;
}
Which lets you write a compact one-liner (the -l
option automatically adds newlines to each print, among other things):
perl -lne 'print for /Total Successful Transactions = (\d+)/'
Just wanted to reframe the previous answers a bit differently; note that in this case:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = 3/;'
1
... we get 1 being printed out - as in "yes, I got a match". If we want to return the matched text portion, as @markusk pointed out, "use parentheses in regex to capture substrings":
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/;'
Xy = 3
However, note that you may have a problem concatenating strings with this idiom, when capturing:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = 3/ . "\n";'
1 # OK
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/ . "\n";'
1 # NOT OK
... so probably better to keep things separate in that case:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/ ; print "\n";'
Xy = 3 # OK again
However, if we want to capture "something", say a digit - then, since we use parentheses, we automatically return just that match with this idiom (not the entire "searched for" string):
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = (\d)/ ; \
print "\n";'
3
... thus, to capture the searched string in its entirety, we should wrap it again in parentheses:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = (\d))/ ; \
print "\n";'
Xy = 33
.... but, we don't get what we expect, because now there are two matches, $1
and $2
; and apparently the idiom "print $str =~ /.../
" outputs all matches (in this case, "$1$2
").
So to get just the searched string in this nested matches case, we now have to explicitly specify only $1
:
$ perl -e '$str="the variable Xy = 3 in this case"; $str =~ /(Xy = (\d))/ ; \
print "$1 \n";'
Xy = 3
EDIT oct 2013: Via Assign one of multiple regex matches to variable as Perl one-liner (dereference array?) - also this can be done for a one liner:
$ perl -e '$str="the variable Xy = 3 in this case"; \
print ( ( $str =~ /(Xy = (\d))/ )[1] ); print "\n";'
3
... however, note the need for a second enveloping set of parentheses for the print
to work directly with the regex returned (anonymous?) array.
Finally, in a multiline context, make sure to first "slurp" the entire file/text into a single string; then use the /s
(single line mode = newline is matched) and /g
(global/multiple matches) - and finally, make sure the match expression is in a while
loop, so as to iterate through all the matches:
$ echo "some data
IN
123
OUT
some more data
is about to follow:
IN
256
OUT
done with data
out" | perl -e '$str = do { local $/; <> }; while ($str =~ /(IN(.*?)OUT)/sg) { print "$1\n"} '
IN
123
OUT
IN
256
OUT
Well, hope this helps someone,
Cheers!