perlpass-by-referencecall-by-valueevaluation-strategy

If perl is call-by-reference why does this happen?


I've read that perl uses call-by-reference when executing subrutines. I made a simple piece of code to check this property, but it behaves like if perl was call-by-value:

$x=50;
$y=70;

sub interchange {
    ($x1, $y1) = @_;

    $z1 = $x1;
    $x1 = $y1;
    $y1 = $z1;

    print "x1:$x1 y1:$y1\n";
}

&interchange ($x, $y);

print "x:$x y:$y\n";

This produces the following output:

$ perl example.pl
x1:70 y1:50
x:50 y:70

If arguments were treated in a call-by-reference way, shouldn't x be equal to x1 and y equal to y1?


Solution

  • To modify the values outside of the sub, you would have to modify the values of @_.

    The following sub interchange does modify the values:

    sub interchange {
        ($x1, $y1) = @_; # this line copies the values to 2 new variables
    
        $z1 = $x1;
        $x1 = $y1;
        $y1 = $z1;
    
        $_[0] = $x1; # this line added to change value outside sub
        $_[1] = $y1; # this line added to change value outside sub
    
        print "x1:$x1 y1:$y1\n";
    }
    

    This gives the output:

    x1:70 y1:50
    x:70 y:50
    

    More info here: http://www.cs.cf.ac.uk/Dave/PERL/node51.html

    But, to quote the article:

    You can see that the function was able to affect the @array variable in the main program. Generally, this is considered bad programming practice because it does not isolate what the function does from the rest of the program.