HiveBrain v1.2.0
Get Started
← Back to all entries
patternMinor

Get sum of an array in 3 ways, for, while and recursive

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
whilearraywaysrecursivegetforsumand

Problem

So i was trying to find sum of an array using 3 ways in perl6

  • for



  • while



  • recursive



(I know there are inbuilt perl6 functions for this)

I want to know if there is a better way to do this or is this it?

sub sumFor(@list)
{
   my $sum = 0;
   for (@list)
   {
      $sum += $_;
   }
   return $sum;
}

sub sumWhile(@list)
{
   my $sum = 0;
   my $index = 0;
   while ($index < @list.elems)
   {
      $sum += @list[$index++];
   }
   return $sum;
}

sub sumRec(@list, $index = 0)
{
   my $sum = 0;
   if ($index < @list.elems)
   {
      $sum = @list[$index] + sumRec(@list,$index+1);
   }
   return $sum;
}

my @list = 1,2,3,4;

say sumFor(@list);
say sumWhile(@list);
say sumRec(@list);

Solution

You may already know the following Perl 6 tidbits, but for others reading along:

-
The ordinary OO way to express the sum of a list of numbers in a variable list is list.sum;

-
The ordinary functional way to express the same thing is sum list;

-
A less common functional idiom that produces the same result is [+] list which is a reduction.

Imo your code is fine. That said:

Parentheses are frequently optional

Larry often pipes up about what he calls "superstitious parens". More generally I think there's a rough consensus among Perl 6 folk that readability for most folk is best served by omitting optional parentheses when the meaning remains clear without them. This is almost always true around conditional expressions. I generally omit them around argument lists too. If I were writing the code you've written I'd likely have dropped seven pairs of "superstitious parens" thus:

sub sumFor(@list)
{
   my $sum = 0;
   for @list
   {
      $sum += $_;
   }
   return $sum;
}

sub sumWhile(@list)
{
   my $sum = 0;
   my $index = 0;
   while $index < @list.elems
   {
      $sum += @list[$index++];
   }
   return $sum;
}

sub sumRec(@list, $index = 0)
{
   my $sum = 0;
   if $index < @list.elems
   {
      $sum = @list[$index] + sumRec @list,$index+1;
   }
   return $sum;
}

my @list = 1,2,3,4;

say sumFor @list;
say sumWhile @list;
say sumRec @list;


Sigils are frequently optional

I don't know of any emerging consensus about use of sigil'd variables vs non-sigil'd variables but you can slash sigils like this:

sub sumRec(\list, \index = 0)
{
   my $sum = 0;
   if index < list.elems
   {
      $sum = list[index] + sumRec(list,index+1);
   }
   return $sum;
}


Stronger typing

Most built in operations accept arguments of a wide range of types and automatically coerce them to fit the operation. This highly generic approach is considered a strength. Thus, for example:

say sum '21', '21'; # 42


This genericity is the default in Perl 6 code. But sometimes you may prefer to explicitly specify types. Thus, perhaps:

subset NumericList of List where .all ~~ Numeric;

sub sumFor(NumericList \list )
{
   my $sum = 0;
   for list
   {
      $sum += $_;
   }
   return $sum;
}

my \list = 1,2,3,4,'a';
say sumFor list; # "Constraint type check failed..."

Code Snippets

sub sumFor(@list)
{
   my $sum = 0;
   for @list
   {
      $sum += $_;
   }
   return $sum;
}

sub sumWhile(@list)
{
   my $sum = 0;
   my $index = 0;
   while $index < @list.elems
   {
      $sum += @list[$index++];
   }
   return $sum;
}

sub sumRec(@list, $index = 0)
{
   my $sum = 0;
   if $index < @list.elems
   {
      $sum = @list[$index] + sumRec @list,$index+1;
   }
   return $sum;
}

my @list = 1,2,3,4;

say sumFor @list;
say sumWhile @list;
say sumRec @list;
sub sumRec(\list, \index = 0)
{
   my $sum = 0;
   if index < list.elems
   {
      $sum = list[index] + sumRec(list,index+1);
   }
   return $sum;
}
say sum '21', '21'; # 42
subset NumericList of List where .all ~~ Numeric;

sub sumFor(NumericList \list )
{
   my $sum = 0;
   for list
   {
      $sum += $_;
   }
   return $sum;
}

my \list = 1,2,3,4,'a';
say sumFor list; # "Constraint type check failed..."

Context

StackExchange Code Review Q#152057, answer score: 5

Revisions (0)

No revisions yet.