in reply to Switch the odd/even elements of an array

sub swap{ reverse( shift, shift ), @_ ? swap( @_ ) : (); } print swap( 1 .. 8 );; 2 1 4 3 6 5 8 7

Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
"Science is about questioning the status quo. Questioning authority".
In the absence of evidence, opinion is indistinguishable from prejudice.

Replies are listed 'Best First'.
Re^2: Switch the odd/even elements of an array
by wind (Priest) on Mar 04, 2011 at 21:27 UTC
    Can always count on you for fun code. To make it a little spookier, maybe inherit the @_:
    sub swap { reverse( shift, shift ), @_ ? &swap : (); }

      Expanding the solution to allow for reversing groups of multiple elements.

      use strict; use warnings; use feature qw{ say }; use List::Util qw{ min }; my @arr = ( 1 .. 9 ); say qq{@arr}; my @twos = reverseGroupsOf( 2, @arr ); say qq{@twos}; my @threes = reverseGroupsOf( 3, @arr ); say qq{@threes}; my @fours = reverseGroupsOf( 4, @arr ); say qq{@fours}; sub reverseGroupsOf { my $groupsOf = shift; my $rcReverse; $rcReverse = sub { reverse( map shift, 1 .. min scalar( @_, $groupsOf ), @_ ? &$rcReverse : (); }; &$rcReverse; }
      1 2 3 4 5 6 7 8 9 2 1 4 3 6 5 8 7 9 3 2 1 6 5 4 9 8 7 4 3 2 1 8 7 6 5 9

      I hope this is of interest.

      Cheers,

      JohnGG

        I tend to like the mathematical solutions instead.

        The following would let you reverse any N elements at a time in an array.

        my @foo = (1..15); my $n = 5; my @bar = @foo[map {$_ + $n - 1 - 2 * ($_ % $n)} (0..$#foo)]; print "@bar";

        Outputs

        5 4 3 2 1 10 9 8 7 6 15 14 13 12 11

        Obviously not as spiffy as using xor to switch odds and evens, but still pretty concise.

        Alternatively, if you want to do a rotation of the elements instead of a reversal, you can use the following translation:

        my @foo = (1..15); my $n = 5; my $i = 2; my @bar = @foo[map {my $r = $_ % $n; $_ - $r + (($r + $i) % $n)} (0..$ +#foo)]; print "@bar";

        Outputs

        3 4 5 1 2 8 9 10 6 7 13 14 15 11 12

        - Miller