Mossroy Mossroy - 5 months ago 15
Perl Question

Why does my Perl sub receive the parameters of its parent?

Here is my test code :

#!/bin/perl
use strict;
use Array::Utils qw[array_minus];

sub sub1 {
my @array1 = qw(1 2 3);
my @array2 = qw(1 3 5);
my @arrayMinus = array_minus(@array1, @array2);
my @sortedArrayMinus = sort @arrayMinus;
print "Result from array_minus + sort : " . join(",", @sortedArrayMinus) . "\n";
my @sortedArrayMinus2 = sort array_minus(@array1, @array2);
print "Result from sort array_minus : " . join(",", @sortedArrayMinus2) . "\n";
}

sub1("a","b");


When I run it, it gives the following result :

Result from array_minus + sort : 2
Can't use string ("b") as an ARRAY ref while "strict refs" in use at Array/Utils.pm line 123.


So, the second call to array_minus fails because of wrong parameters.

I'm using version 0.5 of the Array::Utils library (I've manually copied it from http://cpansearch.perl.org/src/ZMIJ/Array-Utils-0.5/Utils.pm)
The relevant lines of this file are :

sub array_minus(\@\@) {
my %e = map{ $_ => undef } @{$_[1]};
return grep( ! exists( $e{$_} ), @{$_[0]} );
}


If I debug the value of @_ in array_minus, its value is OK for the first call, but it's [ 'a', 'b' ] for the second call.

So it behaves as if array_minus sub receives the parameters of sub1, instead of the ones I passed, but only when I also ask to sort the result on the same line. What's wrong in my code?
I'm using Perl 5.22.1.

Answer

Read the warning in sort and fix the syntax:

my @sortedArrayMinus2 = sort(array_minus(@array1, @array2));

The original syntax was telling sort to use array_minus as the comparison function.

Comments