From 92ded7e7669934eeec6d9c04448c550b3530cd81 Mon Sep 17 00:00:00 2001 From: drbaggy Date: Wed, 17 Feb 2021 06:11:48 +0000 Subject: add code to make fns non destructive - and a "test" to test this --- challenge-100/james-smith/perl/ch-2.pl | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/challenge-100/james-smith/perl/ch-2.pl b/challenge-100/james-smith/perl/ch-2.pl index 6ffe7fc6e3..46a05310f1 100644 --- a/challenge-100/james-smith/perl/ch-2.pl +++ b/challenge-100/james-smith/perl/ch-2.pl @@ -6,6 +6,15 @@ use warnings; use feature qw(say); use Test::More; +## A little check to see if the sum functions are +## non-destructive... +my @Q = ( [1],[2,4],[6,4,9],[5,1,7,2] ); +triangle_sum_1point5_liner( @Q ); +is( triangle_sum_1point5_liner( @Q ), 8 ); +@Q = ( [1],[2,4],[6,4,9],[5,1,7,2] ); +triangle_sum( @Q ); +is( triangle_sum( @Q ), 8 ); + is( triangle_sum( [1],[2,4],[6,4,9],[5,1,7,2] ), 8 ); is( triangle_sum( [3],[3,1],[5,2,3],[4,3,1,3] ), 7 ); is( triangle_sum( [3],[3,1],[3,8,9],[4,3,1,3] ), 12 ); @@ -37,7 +46,7 @@ display_sum( [3],[6,4],[5,2,7],[9,1,8,6] ); ## repeating until the triangle only has a single cell the answer.. sub triangle_sum { - my @tri = @_; + my @tri = map{ [@{$_}] } @_; while(@tri>1) { ## Strip off base of triangle... my $b = pop @tri; @@ -49,6 +58,11 @@ sub triangle_sum { return $tri[0][0]; } +## First thing we do is make a deep copy of @_ as this like the +## previous function is destructive. @_ is an array of references +## and although manipulating @_ doesn't affect the variable passed +## in it does affect the contents of any references passed in. +## ## We can convert the inner for loop into a map... and pop the value ## of $b in the while clause so we can simplify this down to a single ## one line statement, with the return just returning the last @@ -57,6 +71,7 @@ sub triangle_sum { ## so not quite a 1 liner - but close enough!! sub triangle_sum_1point5_liner { + @_ = map{ [@{$_}] } @_; ## Deep copy as destructive.. @{$_[-1]} = map { $_[-1][$_] + $b->[ $b->[$_] < $b->[$_+1] ? $_ : $_+1 ] } 0..@_-1 while @{$b=pop @_}>1; -- cgit