diff options
Diffstat (limited to 'challenge-059/jaredor/perl/ch-1.pl')
| -rwxr-xr-x | challenge-059/jaredor/perl/ch-1.pl | 67 |
1 files changed, 67 insertions, 0 deletions
diff --git a/challenge-059/jaredor/perl/ch-1.pl b/challenge-059/jaredor/perl/ch-1.pl new file mode 100755 index 0000000000..14a277516d --- /dev/null +++ b/challenge-059/jaredor/perl/ch-1.pl @@ -0,0 +1,67 @@ +#!/usr/bin/env perl + +use v5.012; +use warnings; +use Getopt::Long; +use List::Util qw(all); +use Scalar::Util qw(looks_like_number); + +# PWC 059, TASK #1 : Linked List + +Getopt::Long::Configure( 'bundling_values', 'ignorecase_always', + 'pass_through' ); + +GetOptions( 'k=f' => \( my $k ) ); + +die "The --k option must set a numeric value for the partitioning definition." + unless looks_like_number $k; + +die "The link values of the linked list must all be numeric." + unless all { looks_like_number $_ } @ARGV; + +die "No link values provided for the linked list." + unless @ARGV; + +# Convenience constructs. + +use constant NULL => []; +sub make_link { return [ $_[0], NULL ]; } + +# Create the linked list from the input arguments. + +my $ll_input = make_link; +my $ll_curpt = $ll_input; + +$ll_curpt = ( $ll_curpt->[1] = make_link $_ ) for @ARGV; +$ll_input = pop @$ll_input; + +# Split the input linked list into "<" and ">=" linked lists. +# This is a destructive rearrangement of the $ll_input linked list. + +my ( $lt_subll, $ge_subll ) = ( make_link, make_link ); +my ( $lt_curpt, $ge_curpt ) = ( $lt_subll, $ge_subll ); + +while (@$ll_input) { + my $curr_ptr = $ll_input->[0] < $k ? \$lt_curpt : \$ge_curpt; + $ll_input = ( $$curr_ptr = ( $$curr_ptr->[1] = $ll_input ) )->[1]; +} + +( $lt_curpt->[1], $ge_curpt->[1] ) = ( NULL, NULL ); +( $lt_subll, $ge_subll ) = ( pop @$lt_subll, pop @$ge_subll ); + +# Attach the ">=" linked list to the "<" list if "<" exists. + +$lt_curpt->[1] = $ge_subll if defined $lt_subll->[0]; + +# Create output re-linked list. + +my $ll_ltge = defined $lt_subll->[0] ? $lt_subll : $ge_subll; + +# Print linked list data from head to tail. +# This is a non-destructive walk of the $ll_ltge linked list. + +my ( $ll_print, $delim, @outlist ) = ( $ll_ltge, ' -> ', ); + +( $outlist[@outlist], $ll_print ) = @$ll_print while @$ll_print; + +say join( $delim, @outlist ); |
