sub naive_shuffle { my \$n = my @p = @_; for my \$i ( 0..\$n-1 ) { my \$j = int rand \$n; @p[ \$i, \$j ] = @p[ \$j, \$i ]; # swap } return @p; } ##```## # untested sub naive_shuffle_rec { my \$i = shift; my \$n = my @p = @_; my \$j = int rand \$n; @p[ \$i, \$j ] = @p[ \$j, \$i ]; # swap return ++\$i < \$n ? naive_shuffle_rec( \$i, @p ) : @p; } ##``````## sub naive_shuffle_traverse { my \$i = shift; my \$j = shift; my \$n = my @p = @_; @p[ \$i, \$j ] = @p[ \$j, \$i ] if defined \$j; # swap if ( ++\$i < \$n ) { for my \$j (0..\$n-1) { naive_shuffle_traverse( \$i, \$j, \$tally, @p ); } } else { return; } } ##``````## naive_shuffle_traverse(-1, undef, 1..3); ##``````## sub naive_shuffle_count { my \$i = shift; my \$j = shift; my \$tally = shift; my \$n = my @p = @_; @p[ \$i, \$j ] = @p[ \$j, \$i ] if \$j > -1; if ( ++\$i < \$n ) { for my \$j (0..\$n-1) { naive_shuffle_count( \$i, \$j, \$tally, @p ); } } else { \$tally->{ "@p" }++; return; } } ##``````## my %tally = (); naive_shuffle_count( -1, undef, \%tally, 1..3 ); ##``````## DB<2> x \%tally 0 HASH(0x82d7f94) '1 2 3' => 4 '1 3 2' => 5 '2 1 3' => 5 '2 3 1' => 5 '3 1 2' => 4 '3 2 1' => 4 ##``````## sub random_perm { my \$n = my @p = @_; for ( my \$i = \$#p; \$i > 0; --\$i ) { my \$j = int rand( \$i + 1 ); @p[ \$i, \$j ] = @p[ \$j, \$i ]; } return @p; } ```