Card shuffles: Difference between revisions

Rename Perl 6 -> Raku, alphabetize, minor clean-up
(Rename Perl 6 -> Raku, alphabetize, minor clean-up)
Line 224:
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[20, 17, 18, 19, 14, 15, 16, 10, 11, 12, 13, 9, 8, 7, 5, 6, 1, 2, 3, 4]</pre>
 
=={{header|C sharp|C#}}==
{{trans|Java}}
<lang csharp>using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
 
namespace CardShuffles {
public static class Helper {
public static string AsString<T>(this ICollection<T> c) {
StringBuilder sb = new StringBuilder("[");
sb.Append(string.Join(", ", c));
return sb.Append("]").ToString();
}
}
 
class Program {
private static Random rand = new Random();
 
public static List<T> riffleShuffle<T>(ICollection<T> list, int flips) {
List<T> newList = new List<T>(list);
 
for (int n = 0; n < flips; n++) {
//cut the deck at the middle +/- 10%, remove the second line of the formula for perfect cutting
int cutPoint = newList.Count / 2
+ (rand.Next(0, 2) == 0 ? -1 : 1) * rand.Next((int)(newList.Count * 0.1));
 
//split the deck
List<T> left = new List<T>(newList.Take(cutPoint));
List<T> right = new List<T>(newList.Skip(cutPoint));
 
newList.Clear();
 
while (left.Count > 0 && right.Count > 0) {
//allow for imperfect riffling so that more than one card can come form the same side in a row
//biased towards the side with more cards
//remove the if and else and brackets for perfect riffling
if (rand.NextDouble() >= ((double)left.Count / right.Count) / 2) {
newList.Add(right.First());
right.RemoveAt(0);
}
else {
newList.Add(left.First());
left.RemoveAt(0);
}
}
 
//if either hand is out of cards then flip all of the other hand to the shuffled deck
if (left.Count > 0) newList.AddRange(left);
if (right.Count > 0) newList.AddRange(right);
}
 
return newList;
}
 
public static List<T> overhandShuffle<T>(List<T> list, int passes) {
List<T> mainHand = new List<T>(list);
 
for (int n = 0; n < passes; n++) {
List<T> otherHand = new List<T>();
 
while (mainHand.Count>0) {
//cut at up to 20% of the way through the deck
int cutSize = rand.Next((int)(list.Count * 0.2)) + 1;
 
List<T> temp = new List<T>();
 
//grab the next cut up to the end of the cards left in the main hand
for (int i = 0; i < cutSize && mainHand.Count > 0; i++) {
temp.Add(mainHand.First());
mainHand.RemoveAt(0);
}
 
//add them to the cards in the other hand, sometimes to the front sometimes to the back
if (rand.NextDouble()>=0.1) {
//front most of the time
temp.AddRange(otherHand);
otherHand = temp;
}
else {
//end sometimes
otherHand.AddRange(temp);
}
}
 
//move the cards back to the main hand
mainHand = otherHand;
}
 
return mainHand;
}
 
static void Main(string[] args) {
List<int> list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = riffleShuffle(list, 10);
Console.WriteLine(list.AsString());
Console.WriteLine();
 
list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = riffleShuffle(list, 1);
Console.WriteLine(list.AsString());
Console.WriteLine();
 
list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = overhandShuffle(list, 10);
Console.WriteLine(list.AsString());
Console.WriteLine();
 
list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = overhandShuffle(list, 1);
Console.WriteLine(list.AsString());
Console.WriteLine();
}
}
}</lang>
{{out}}
<pre>[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[9, 2, 8, 3, 20, 15, 1, 13, 7, 18, 5, 16, 4, 19, 10, 6, 12, 14, 11, 17]
 
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[12, 1, 2, 3, 4, 13, 14, 5, 15, 16, 6, 7, 17, 8, 18, 19, 9, 10, 20, 11]
 
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[13, 18, 12, 17, 10, 9, 19, 11, 16, 15, 6, 8, 14, 1, 3, 2, 5, 4, 7, 20]
 
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[20, 17, 18, 19, 15, 16, 11, 12, 13, 14, 10, 7, 8, 9, 5, 6, 2, 3, 4, 1]</pre>
 
=={{header|C++}}==
Line 370 ⟶ 502:
14 4 17 3 12 5 19 6 20 2 16 11 8 15 7 13 10 18 9 1
</pre>
 
=={{header|C#|C sharp}}==
{{trans|Java}}
<lang csharp>using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
 
namespace CardShuffles {
public static class Helper {
public static string AsString<T>(this ICollection<T> c) {
StringBuilder sb = new StringBuilder("[");
sb.Append(string.Join(", ", c));
return sb.Append("]").ToString();
}
}
 
class Program {
private static Random rand = new Random();
 
public static List<T> riffleShuffle<T>(ICollection<T> list, int flips) {
List<T> newList = new List<T>(list);
 
for (int n = 0; n < flips; n++) {
//cut the deck at the middle +/- 10%, remove the second line of the formula for perfect cutting
int cutPoint = newList.Count / 2
+ (rand.Next(0, 2) == 0 ? -1 : 1) * rand.Next((int)(newList.Count * 0.1));
 
//split the deck
List<T> left = new List<T>(newList.Take(cutPoint));
List<T> right = new List<T>(newList.Skip(cutPoint));
 
newList.Clear();
 
while (left.Count > 0 && right.Count > 0) {
//allow for imperfect riffling so that more than one card can come form the same side in a row
//biased towards the side with more cards
//remove the if and else and brackets for perfect riffling
if (rand.NextDouble() >= ((double)left.Count / right.Count) / 2) {
newList.Add(right.First());
right.RemoveAt(0);
}
else {
newList.Add(left.First());
left.RemoveAt(0);
}
}
 
//if either hand is out of cards then flip all of the other hand to the shuffled deck
if (left.Count > 0) newList.AddRange(left);
if (right.Count > 0) newList.AddRange(right);
}
 
return newList;
}
 
public static List<T> overhandShuffle<T>(List<T> list, int passes) {
List<T> mainHand = new List<T>(list);
 
for (int n = 0; n < passes; n++) {
List<T> otherHand = new List<T>();
 
while (mainHand.Count>0) {
//cut at up to 20% of the way through the deck
int cutSize = rand.Next((int)(list.Count * 0.2)) + 1;
 
List<T> temp = new List<T>();
 
//grab the next cut up to the end of the cards left in the main hand
for (int i = 0; i < cutSize && mainHand.Count > 0; i++) {
temp.Add(mainHand.First());
mainHand.RemoveAt(0);
}
 
//add them to the cards in the other hand, sometimes to the front sometimes to the back
if (rand.NextDouble()>=0.1) {
//front most of the time
temp.AddRange(otherHand);
otherHand = temp;
}
else {
//end sometimes
otherHand.AddRange(temp);
}
}
 
//move the cards back to the main hand
mainHand = otherHand;
}
 
return mainHand;
}
 
static void Main(string[] args) {
List<int> list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = riffleShuffle(list, 10);
Console.WriteLine(list.AsString());
Console.WriteLine();
 
list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = riffleShuffle(list, 1);
Console.WriteLine(list.AsString());
Console.WriteLine();
 
list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = overhandShuffle(list, 10);
Console.WriteLine(list.AsString());
Console.WriteLine();
 
list = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
Console.WriteLine(list.AsString());
list = overhandShuffle(list, 1);
Console.WriteLine(list.AsString());
Console.WriteLine();
}
}
}</lang>
{{out}}
<pre>[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[9, 2, 8, 3, 20, 15, 1, 13, 7, 18, 5, 16, 4, 19, 10, 6, 12, 14, 11, 17]
 
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[12, 1, 2, 3, 4, 13, 14, 5, 15, 16, 6, 7, 17, 8, 18, 19, 9, 10, 20, 11]
 
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[13, 18, 12, 17, 10, 9, 19, 11, 16, 15, 6, 8, 14, 1, 3, 2, 5, 4, 7, 20]
 
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20]
[20, 17, 18, 19, 15, 16, 11, 12, 13, 14, 10, 7, 8, 9, 5, 6, 2, 3, 4, 1]</pre>
 
=={{header|D}}==
Line 1,427:
<pre>9 11 5 2 4 14 1 3 8 6 15 13 16 12 19 20 7 18 10 17
1 10 19 9 18 8 17 7 16 6 15 5 14 4 13 3 12 2 11 20</pre>
 
=={{header|Perl 6}}==
 
<lang perl6>use v6;
 
sub overhand ( @cards ) {
my @splits = roll 10, ^( @cards.elems div 5 )+1;
@cards.rotor( @splits ,:partial ).reverse.flat
}
 
sub riffle ( @pile is copy ) {
my @pile2 = @pile.splice: @pile.elems div 2 ;
 
roundrobin(
@pile.rotor( (1 .. 3).roll(7), :partial ),
@pile2.rotor( (1 .. 3).roll(9), :partial ),
).flat
}
 
my @cards = ^20;
@cards.=&overhand for ^10;
say @cards;
 
my @cards2 = ^20;
@cards2.=&riffle for ^10;
say @cards2;
 
say (^20).pick(*);
</lang>
 
=={{header|Phix}}==
Line 1,807 ⟶ 1,778:
shuffle: (J♣ 2♠ 4♦ A♦ K♥ 6♦ 5♦ 8♣ 2♦ T♥ 4♠ 3♣ 7♦ 9♠ T♦ J...
</pre>
 
=={{header|Raku}}==
(formerly Perl 6)
 
<lang perl6>use v6;
 
sub overhand ( @cards ) {
my @splits = roll 10, ^( @cards.elems div 5 )+1;
@cards.rotor( @splits ,:partial ).reverse.flat
}
 
sub riffle ( @pile is copy ) {
my @pile2 = @pile.splice: @pile.elems div 2 ;
 
roundrobin(
@pile.rotor( (1 .. 3).roll(7), :partial ),
@pile2.rotor( (1 .. 3).roll(9), :partial ),
).flat
}
 
my @cards = ^20;
@cards.=&overhand for ^10;
say @cards;
 
my @cards2 = ^20;
@cards2.=&riffle for ^10;
say @cards2;
 
say (^20).pick(*);
</lang>
 
=={{header|REXX}}==
10,327

edits