Подтвердить что ты не робот

Perl Regex - печать совпадающего значения

Что такое регулярное выражение perl для печати согласованного значения? Например, я хочу напечатать 195 из этой строки

"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".

Как я могу это сделать? Спасибо заранее

4b9b3361

Ответ 1

Вы можете использовать круглые скобки в регулярном выражении для захвата подстрок. Захваченные группы хранятся в $1, $2 и т.д. Пример:

while (<>) {
    if (/Total Successful Transactions = (\d+)/) {
        print "$1\n";
    }
}

или, несколько короче:

while (<>) {
    print "$1\n" if /Total Successful Transactions = (\d+)/;
}

Ответ 2

Просто хотелось немного перефразировать предыдущие ответы; обратите внимание, что в этом случае:

$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = 3/;'
1 

... мы получаем, что 1 печатается - как в "да, я получил матч". Если мы хотим вернуть согласованную текстовую часть, как указано @markusk, "использовать круглые скобки в регулярном выражении для захвата подстрок":

$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/;'
Xy = 3

Однако обратите внимание, что у вас может возникнуть проблема с конкатенацией строк с этой идиомой при захвате:

$ 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

... поэтому, вероятно, лучше держать вещи в этом случае:

$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/ ; print "\n";'
Xy = 3 # OK again

 

Однако, если мы хотим захватить "что-то", скажем цифру, то, поскольку мы используем круглые скобки, мы автоматически возвращаем именно это соответствие этой идиоме (а не всей строке "поиск" ):

$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = (\d)/ ; \
print "\n";'
3

... таким образом, чтобы зафиксировать искомую строку целиком, мы должны ее снова скопировать в круглые скобки:

$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = (\d))/ ; \
print "\n";'
Xy = 33

.... но мы не получаем того, чего ожидаем, потому что теперь есть два совпадения, $1 и $2; и, по-видимому, идиома "print $str =~ /.../" выводит все совпадения (в этом случае "$1$2" ).

Итак, чтобы получить только искомую строку в этом случае с вложенными совпадениями, теперь мы должны явно указать только $1:

$ perl -e '$str="the variable Xy = 3 in this case"; $str =~ /(Xy = (\d))/ ; \
print "$1 \n";'
Xy = 3 

EDIT oct 2013: Via Присвоить одно из нескольких совпадений регулярных выражений переменной как Perl one-liner (массив разыменования?) - также это может быть сделано для одного лайнера

$ perl -e '$str="the variable Xy = 3 in this case"; \
print ( ( $str =~ /(Xy = (\d))/ )[1] ); print "\n";'
3

... однако обратите внимание на необходимость использования второго огибающего набора круглых скобок для print для работы с массивом возвращенных (анонимных?) регулярных выражений.

 

Наконец, в многострочном контексте убедитесь, что сначала "slurp" весь файл/текст в одну строку; затем используйте /s (однолинейный режим = соответствие новой строки) и /g (глобальные/множественные совпадения) - и, наконец, убедитесь, что выражение соответствия находится в цикле while, чтобы перебирать все совпадения:

$ 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

Хорошо, надеюсь, это поможет кому-то,
Ура!

Ответ 3

Как насчет просто:

print $string =~ /Total Successful Transactions = (\d+)/;

Вам редко приходится использовать $1 и друзей.

Ответ 4

/(\d+$)/;
print $1;

Я думаю, вы просто хотите номер 195. Правильно?

Ответ 5

Проверьте цифры в конце перед " и ..

#!/usr/bin/env perl

use strict;
use warnings;

my $string = q{"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".};
my ($number) = $string =~ m{ (\d+) " \. \z}x;

print "Matched number: $number\n" if defined $number;

Ответ 6

my $str = '"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".';

$str =~ /Total Successful Transactions = (\d+)/;
print $1; 

195 будет храниться в $1

Ответ 7

Версия командной строки принятого ответа @markusk довольно компактна:

perl -ne '/Total Successful Transactions = (\d+)/ && print "$1\n";'

Ответ 8

Так же:

if ("2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195" =~ /(\d+)$/) {
    print $1;
}

После сопоставления сопоставленные группы становятся доступными как $1.. $n.