15

I thought there would have been a simple answer for this somewhere on the internet but it seems like I'm having trouble finding a solution. I'm first of all wondering if there's a simple method or function for this:

e.g. ~~ or array.contains() from Perl 5

It would also be nice to know how many different ways of achieving this result there are in Perl 6 as some might be better than others given the situation of the problem.

Pat
  • 36,282
  • 18
  • 72
  • 87
Phyreprooph
  • 517
  • 2
  • 13

3 Answers3

14
my @a = <foo bar buzz>;
say so 'bar' ∈ @a;
say so @a ∋ 'buzz';
# OUTPUT«True␤True␤»

As documented in http://doc.perl6.org/language/setbagmix and defined in https://github.com/rakudo/rakudo/blob/nom/src/core/set_operators.pm .

I believe that Set checks for equivalence, if you need identity you will have to loop over the array and === it.

You could turn the Array into a Set and use subscripts.

say @a.Set{'bar'};
# OUTPUT«True␤»
say @a.Set<bar buzz>;
# OUTPUT«(True True)␤»
Martijn Pieters
  • 1,048,767
  • 296
  • 4,058
  • 3,343
  • Note that there are huge performance consequences for using an array as a set, especially when doing so repeatedly. In that case, you really need to do something like `my $s = @a.Set;` outside the loop, and do `$elem ∈ $s` in the loop. – mscha Feb 17 '16 at 22:42
11

Another way to do this, is:

my @a = <foo bar buzz>;
if 'bar' eq any(@a) {
    say "yes";
}
# OUTPUT«yes␤»
mscha
  • 6,509
  • 3
  • 24
  • 40
5

Sub first documentation. sub first returns the matching element or Nil. Nil is a falsey value meaning you can use the result in a Bool context to determine if the array contains matching element.

my @a = 'A'..'Z';
say 'We got it' if @a.first('Z');
say 'We didn\'t get it' if !@a.first(1);

There are several adverbs to sub first which change the results. For instance to return the index instead of the element it is possible use the :k adverb. In this example we also topicalize the result for use within the if statement:

my @a = 'A'..'Z';
if @a.first('Q', :k) -> $index {
    say $index;
}
ZzZombo
  • 1,082
  • 1
  • 11
  • 26
J Hall
  • 531
  • 3
  • 10