2015-03-31 2 views
-2

Я хотел бы проверить, появляется ли строка в массиве более одного раза. Есть способ, который я нашел, но он требует установить что-то из CPAN. У меня нет доступа root для установки модуля CPAN, поэтому я бы предпочел сделать это без использования CPAN.Как проверить, отображается ли строка в массиве более одного раза?

+1

'perldoc -f grep' – toolic

+3

Во-первых, вы не должны быть' root' использовать модули CPAN, но это другая тема. Во-вторых, что вы пробовали **? Вы даже не можете написать простой цикл для прохождения массива? –

+0

Как называется модуль CPAN, который вы нашли? Какие функции казались полезными? что ты уже испробовал? Вы можете незначительно улучшить этот вопрос (это действительно FAQ), добавив немного больше информации, чтобы он стал полезным для других пользователей SO. –

ответ

1
my $count = grep $_ eq $word, @array; 

См. perldoc -f grep.

Вычисляет BLOCK или EXPR для каждого элемента LIST (локально настройки $_ к каждому элементу) и возвращает значение списка, состоящего из тех элементов, для которых выражение оценивали с истинным. В скалярном контексте возвращает количество раз, когда выражение было истинным.

1

Редактировать: Я предположил, что ваша «строка» не обязательно является дискретным элементом. Чтобы подсчитать каждый элемент, который полностью соответствует, затяните совпадение (т. Е. С /^...$/) или используйте eq, как указывает Синан в комментариях.


Вы можете подсчитать количество раз grep соответствует строке в массиве:

my @animals = qw/duck goose camel squirrel camel camelback/ ; 

if (scalar (grep { /^camel$/ } @animals) > 1) { 
    print "more than one" ; 
} 

Более короткие формы:

say "more" if (grep /^camel$/, @animals) > 1 ; 
say ~~(grep /^camel$/, @animal); 

"~~" коротка для "scalar" здесь.

+0

oops yup '~~' не нужно с 'if' ... забыл. Благодарю. Обычно я использую эти короткие строки в 're.pl' или debugger для подсчета согласованных элементов вместо подсчета точного числа. Я загружаю свои любимые модули (для подсчета использую «true»). Я разгромил вещи более одного раза с помощью grep = "camel", @ animals' (вместо 'eq'). Извините за неряшливость. Будет исправлено для потомства. –

+0

@ SinanÜnür - Отредактировано согласно комментарию. Благодарю. –

1

При обращении за помощью в Stack Overflow обычно ожидается, что вы покажете нам код, который поможет вам с. Это не место, где можно получить краш-курс в программировании на Perl.

Самый универсальный способ справиться с этим - построить хеш, чьими ключами являются все различные значения в списке, а значения - это количество раз, когда этот элемент встречается. Эта программа делает именно то, что найти значения, которые происходят несколько раз

use strict; 
use warnings; 
use 5.010; 

my @animals = qw/ duck goose camel squirrel camel /; 

my %counts; 
++$counts{$_} for @animals; 

say for grep $counts{$_} > 1, keys %counts; 

выход

camel 

Или, если у вас есть определенное значение, которое вы хотите проверить, происходит ли это несколько раз, вы можете запросить хэш непосредственно

if ($counts{goose} > 1) { 
    ... 
} 
+0

«'% seen' hash », по-видимому, самый идиоматический и надежный способ сделать это (с' grep $ _ eq $ match, @array; 'будучи самым простым, но более склонным к PEBKAC для меня). В качестве бонуса вы делаете '++ $ count {$ _}' выглядеть короче и сладким здесь :-) Не было бы более явного синтаксиса (но по-своему по-своему), например 'count (" string ", @array)' сделать полезное дополнение к «List :: Util' или« List :: MoreUtils »? –

+0

Итак, теперь я хочу узнать о прототипах? ... Или, ну, как сделать 'sub count ($ @) {my $ string = shift; scalar grep $ _ eq $ string, @_} 'или' sub count ($ @) {my $ s = shift; мой% count; ++ $ count {$ _} для @_; return $ count {$ s}; } 'чувствовать себя более" встроенным ". –

+0

Просто отметив, что это не моя идея ... так что может быть не так уж плохо ;-) * например * ['autobox :: Core'] (http://www.metacpan.org/pod/autobox :: Core) делает что-то, что кажется «ключевым», в котором участвует «' -> count() '::« say [qw/camel squirrel duck camelhair camel goose /] -> count ("camel") '. Но это только «ядро», как в «autobox :: Core» –

Смежные вопросы