Самый быстрый способ извлечь ведущий текст с помощью Perl - PullRequest
1 голос
/ 16 декабря 2011

У меня есть что-то вроде $string = ABC_RPM_LOL и GELO_FRE_OPN Я хотел бы извлечь ABC и GELO.(Слово перед первым подчеркиванием).

Каков самый быстрый способ добиться этого с помощью Perl?

Ответы [ 6 ]

5 голосов
/ 16 декабря 2011

Можно использовать следующее регулярное выражение:

$string =~ /^([A-Z]+)_/;
$value = $1;

Это предполагает, что ваши слова состоят только из заглавных букв.Если это смешанный регистр, добавьте i в конце регулярного выражения: /^([A-Z]+)_/i.

Редактировать: Так как вы попросили самый быстрый способ, вот сравнительный тест моегоregex и Lazarus's split:

#!perl

use strict;
use warnings;

use Benchmark qw/ :all /;

my $string = "ABC_RPM_LOL";
my $value;

my $count = 10_000_000;
cmpthese( $count, {
    'regex' => sub { $string =~ /^([A-Z]+)_/; $value = $1; },
        'split' => sub { ($value) = split /_/, $string; }
});

Результаты:

           Rate regex split
regex 1869159/s    --  -29%
split 2624672/s   40%    --

Так что split намного быстрее.

Редактирование второго : я добавил три других ответа здесь:

'split2' => sub { $value = (split('_',$string))[0]; },
'split3' => sub { ($value) = split /_/, $string, 2; },
'substr' => sub { $value = substr $string, 0, index $string, '_'; },

И новые результаты:

            Rate  regex split2 split3  split substr
regex  1848429/s     --    -8%   -27%   -28%   -63%
split2 2008032/s     9%     --   -21%   -22%   -60%
split3 2538071/s    37%    26%     --    -1%   -50%
split  2570694/s    39%    28%     1%     --   -49%
substr 5050505/s   173%   152%    99%    96%     --

tadmc's substr ответ является самым быстрым с огромным отрывом.

3 голосов
/ 16 декабря 2011

Мой опыт подсказывает, что Рон новичок в программировании.

«Самый быстрый» очень редко соотносится с «лучшим» ...

Но, если мы действительно хотим быстрее, я бы начал с substr / index:

my $word1 = substr $_, 0, index $_, '_';

Если бы я подумал, что «Quickest» - это не простой случай преждевременной оптимизации, я бы показал несколько разных способов ответить на этот вопрос.

2 голосов
/ 16 декабря 2011

Нет необходимости split в строке более чем в два.

Если в качестве split указан необязательный третий параметр, он будет использовать его для ограничения числа результирующих строк (и впоследствии выполненной работы):

my ( $word ) = split /_/, $str, 2;
1 голос
/ 16 декабря 2011

В одну сторону:

#!/usr/bin/env perl
use strict;
use warnings;
my $string="ABC_RPM_LOL and GELO_FRE_OPN";
my @list = ( $string =~ m{(?:\b|\s)(\w+?)_}g );
print "@list\n";
1 голос
/ 16 декабря 2011

вам нужно что-то вроде

$abc = split('_', $string)[0] # when string = ABC_RPM_LOL
$gelo = split('_', $string)[0] # when string = GELO_FRE_OPN
1 голос
/ 16 декабря 2011

Я бы не использовал Regex для этого, скромная функция split - ваш друг.

$extract = (split(/_/, $string))[0];
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...