Let's say I have a large array, @stuff
, and a $thing
, and I want to know if $thing
is in @stuff
. What's the best way to do that in Perl 6? And with “best” I mean: idiomatic, readable, performant; not necessarily in that order.
There are actually two separate cases. One is where you have to do a lot of checks for different $thing
s, the other is where you only do this once or a few times.
Let's look at the first case first. I think I know the (or a) right answer.
my $set-of-stuff = set @stuff;
for @whatever -> $thing {
do-something-with($thing) if $thing ∈ $set of stuff;
}
You can actually skip the first line and simply say ... if $thing ∈ @stuff
, but that will almost certainly have much worse performance, since the set is created every time.
But now the second case, I only have one $thing
to check.
The above solution works, of course, but creating the set, just to check it once, seems a lot of overhead.
The shortcut
do-something-with($thing) if $thing ∈ @stuff;
makes a little more sense here, since we only call it once. But still, we have to create a set for one use.
A bit more traditional is:
do-something-with($thing) if @stuff.grep($thing);
Or potentially faster:
do-something-with($thing) if @stuff.first($thing);
But this seems less idiomatic, and certainly the second one is less readable than $thing ∈ @stuff
.
I don't think there's a smart match solution, right? Certainly this doesn't work:
do-something-with($thing) if $thing ~~ @stuff;
Any thoughts?
Perl | exists() Function The exists() function in Perl is used to check whether an element in an given array or hash exists or not. This function returns 1 if the desired element is present in the given array or hash else returns 0.
You can check how many times the element in the array (@test) is repeated by counting it in a hash (%seen). You can check how many keys ($size) are present in the hash (%seen). If more than 1 key is present, you know that the elements in the array are not identical.
A list is an ordered collection of scalars. An array is a variable that contains a list. In Perl, the two terms are often used as if they're interchangeable. But, to be accurate, the list is the data, and the array is the variable.
A simple way to check if an array is null or defined is to examine it in a scalar context to obtain the number of elements in the array. If the array is empty, it will return 0, which Perl will also evaluate as boolean false.
Depends on what your definition of "best" or "smart" is.
If you're talking about performance, I'm pretty sure
@stuff.first($thing)
is the fastest.
Idiomatically, and close to the above solution, would be:
$thing ~~ any @stuff
which has the potential of better wallclock performance due to auto-threading.
Using sets to do this, makes the code look closer to formal logic. But it won't make things faster, because the set needs to be created (unless maybe it could be created at compile time).
Not sure there is a "best" answer to this one.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With