user1613245
user1613245

Reputation: 351

Perl 2x2 array addition using Subroutines and Reference

My question in Perl is: Define 2x2 arrays using anonymous lists. Pass the arrays to a subroutine and add them together. Return a reference to sum array and print the values from the main part of the program.

My script is:

#!/usr/bin/perl

use strict;

use warnings;

my @array = ([1,2],[4,5]); 

my $refarray = \@array;

print sumarray($refarray);

sub sumarray

{

 $refarray = shift;

 foreach (@{$refarray})

 {

  $refarray = ($refarray[0]->[0]+$refarray[1]->[0],$refarray[0]->[1]+$refarray[1]->[1]);

 }

 return $refarray;

}

Where am I going wrong? Please help. Thanks in advance.

I am getting the output as 0.

If I use use strict; and use warnings; I will get the error message as

Global symbol "@refarray" requires explicit package name at line 23.
Global symbol "@refarray" requires explicit package name at line 23.
Global symbol "@refarray" requires explicit package name at line 23.
Global symbol "@refarray" requires explicit package name at line 23.
Execution aborted due to compilation errors.

Upvotes: 0

Views: 1173

Answers (3)

memowe
memowe

Reputation: 2668

It could be expressed very simply with a combination of the list operations sum (from the core module List::Util) and map.

Code

#!/usr/bin/env perl
use strict;
use warnings;
use feature 'say';
use List::Util 'sum';

sub sum_square {
    my @arrays = @_;
    return [ map {sum @$_} @arrays ];
}

say join ', ' => @{ sum_square([1,2], [4,5]) };

Output:

3, 9

Since this is Perl, it could be expressed in a more compact way.

Shortification

sub sum_square { [ map {sum @$_} @_ ] }
say join ', ' => @{ sum_square([1,2], [4,5]) };

Shortification2

say join ', ' => map {sum @$_} [1,2], [4,5];

Edit: sum the other way round

If the function should be a column sum instead of a line sum, this modification should do the trick (iterate over the indices of the first array):

sub sum_square {
    my @arrays = @_;
    return [ map { my $i = $_;          # $i: all indices of the first array
        sum map $_->[$i] => @arrays     # sum over all $i-th values of @arrays
    } 0 .. $#{$arrays[0]} ];
}

Output:

5, 7

Upvotes: 2

Rohit Jain
Rohit Jain

Reputation: 213281

Few problems with your code: -

  • First, in your for-loop, you are modifying your reference $refarray which you should not do.
  • Second, $refarray[0]->[0] will not compile. Since $refarray is a reference to an array, you should either use its 1st element using arrow: - $refarray->[0][0], or you need to de-reference it before using the way you are using: - $$refarray[0]->[0].

Having said that, I think you should replace your subroutine with this one: -

use strict;
use warnings;

my @array = ([1,2],[4,5]); 
my $refarray = \@array;

my $sum = sumarray($refarray);
print $sum->[0], $sum->[1];

sub sumarray {
    my $ref = shift;
    return [$ref->[0][0] + $ref->[1][0], $ref->[0][1] + $ref->[1][1]];
}

OUTPUT: -

5 7

Upvotes: 3

mvp
mvp

Reputation: 116217

Try this:

#!/usr/bin/perl -w

my $r = sumarray([1,2],[3,4]);
print $r->[0], " ", $r->[1], "\n";

sub sumarray {
    my ($a, $b) = @_;
    return [
        $a->[0]+$b->[0],
        $a->[1]+$b->[1]
    ];
}

Upvotes: 2

Related Questions