15
\$\begingroup\$

Tonight is card game night! You are the dealer and your task is to write a program to deal the cards to the players.

Given an array of cards and the number of players, you need to split the array of cards into a hand for each player.

example for 4 players with a deck of 10 cards

Rules

Your program will receive an non-empty array A , as well as a non-zero positive integer n. The array should then be split into n hands. If the length of the string isn't divisible by n any leftover cards at the end should be distributed as evenly as possible.

  • If n==1, you will need to return an array of array with A as it's only element
  • If n is greater than the length of A, you will need to return every hand and an empty hand. if n = 4 and array A = [1,2,3], you should return [[1],[2],[3]] or [[1],[2],[3],[]]. You are free to handle the empty hand with empty, undefined or null.

  • The array can contain any type rather than a number.

  • You should not change the order of the array while dealing. For example if n = 2 and A= [1,2,3], any result rather than [[1,3],[2]] will be invalid.

Test Cases

n   A               Output

1   [1,2,3,4,5,6]   [[1,2,3,4,5,6]]
2   [1,2,3,4,5,6]   [[1,3,5],[2,4,6]]
3   [1,2,3,4,5,6]   [[1,4],[2,5],[3,6]]
4   [1,2,3,4,5,6]   [[1,5],[2,6],[3],[4]]
7   [1,2,3,4,5,6]   [[1],[2],[3],[4],[5],[6]] // or [[1],[2],[3],[4],[5],[6],[]]

Demo Program

def deal(cards, n):
	i = 0
	players = [[] for _ in range(n)]
	for card in cards:
		players[i % n].append(card)
		i += 1
	return players

hands = deal([1,2,3,4,5,6], 2)

print(hands)

Try it online!

This is , so you the shortest bytes of each language will be the winner.

Inspired from Create chunks from array by chau giang

\$\endgroup\$
  • 1
    \$\begingroup\$ you will need to return every hands and an empty hand contradicts the last test case's first result possibility. \$\endgroup\$ – Adám Mar 6 at 23:41
  • 6
    \$\begingroup\$ In the future I'd recommend using the Sandbox to iron out problems and gauge community feedback before posting your question to main \$\endgroup\$ – Jo King Mar 6 at 23:42
  • 2
    \$\begingroup\$ @JoKing I fully agree. I didnt think I would have so much edit to do. It is like pushing to prod without deploying on beta first. Thank you for the help. \$\endgroup\$ – aloisdg Mar 6 at 23:43
  • 1
    \$\begingroup\$ @aloisdg I can't parse your suggested alternate rule. If the idea is like people often deal to a circle, then all the players that end up with most cards are at the beginning, and players that are at the end may get no cards. \$\endgroup\$ – Adám Mar 6 at 23:44
  • 2
    \$\begingroup\$ What if the input array contains a 0? \$\endgroup\$ – Shaggy Mar 7 at 9:36

22 Answers 22

12
\$\begingroup\$

05AB1E, 3 1 byte

Saved 2 bytes thanks to Adnan

ι

Try it online! or as a Test Suite

Explanation

ι  # uninterleave

Does exactly what the challenge asks for

\$\endgroup\$
  • 5
    \$\begingroup\$ I think this should work as well: ι \$\endgroup\$ – Adnan Mar 7 at 8:50
  • \$\begingroup\$ @Adnan: Yeah thanks :) Only difference is the empty list for n=7, but that is an acceptable output format. I've totally missed that built-in :/ \$\endgroup\$ – Emigna Mar 7 at 9:06
  • \$\begingroup\$ So there is a language with a built-in for this! :D \$\endgroup\$ – aloisdg Mar 7 at 12:17
9
\$\begingroup\$

R, 46 25 bytes

function(A,n)split(A,1:n)

Try it online!

splits A into groups defined by 1:n, recycling 1:n until it matches length with A.

\$\endgroup\$
7
\$\begingroup\$

Perl 6, 33 24 bytes

->\b{*.classify:{$++%b}}

Try it online!

Anonymous curried code block that takes a number and returns a Whatever lambda that takes a list and returns a list of lists. This takes the second option when given a number larger than the length of lists, e.g. f(4)([1,2,3]) returns [[1],[2],[3]]

Explanation:

->\b{                  }  # Anonymous code block that takes a number
     *                    # And returns a Whatever lambda
      .classify           # That groups by
               :{$++%b}   # The index modulo the number
\$\endgroup\$
7
\$\begingroup\$

Wolfram Language (Mathematica), 28 bytes

(s=#;GatherBy[#2,#~Mod~s&])&

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Very cleverly done! \$\endgroup\$ – Greg Martin Mar 7 at 10:42
  • \$\begingroup\$ "The array can contain any type rather than a number." \$\endgroup\$ – attinat May 8 at 8:40
6
\$\begingroup\$

Japt, 2 bytes

Takes the array as the first input.

óV

Try it

\$\endgroup\$
5
\$\begingroup\$

Python 2, 37 bytes

Code:

lambda x,n:[x[i::n]for i in range(n)]

Try it online!

\$\endgroup\$
5
\$\begingroup\$

Jelly, 6 2 bytes

sZ

Try it online!

Thanks to @JonathanAllan for saving 4 bytes

\$\endgroup\$
  • \$\begingroup\$ Does sZ not work? \$\endgroup\$ – Jonathan Allan Mar 7 at 13:24
  • \$\begingroup\$ @JonathanAllan yes, somehow missed that. Do you want to post as separate answer or shall I edit mine? \$\endgroup\$ – Nick Kennedy Mar 7 at 14:34
  • \$\begingroup\$ No you're welcome to edit :) \$\endgroup\$ – Jonathan Allan Mar 7 at 14:39
4
\$\begingroup\$

J, 13, 11, 10, 9 bytes

(|#\)</.]

Try it online!

how (previous explanation, fundamentally the same)

] </.~ (| #\)
  </.~          NB. box results of grouping
]               NB. the right arg by...
         |      NB. the remainders of dividing...
       [        NB. the left arg into...
           #\   NB. the length of each prefix of...
              ] NB. the right arg,
                NB. aka, the integers 1 thru
                NB. the length of the right arg
\$\endgroup\$
3
\$\begingroup\$

Charcoal, 9 bytes

IEθ✂ηιLηθ

Try it online! Link is to verbose version of code. Takes input in the order [n, A] and outputs each value on its own line and each hand double-spaced from the previous. Explanation:

  θ         First input `n`
 E          Map over implicit range
    η       Second input `A`
   ✂        Sliced
     ι      Starting at current index
      Lη    Ending at length of `A`
        θ   Taking every `n`th element
I           Cast to string
            Implicitly print
\$\endgroup\$
  • \$\begingroup\$ +1 for making the symbol of "slice" a scissors! \$\endgroup\$ – Jonah Mar 7 at 1:21
2
\$\begingroup\$

Haskell, 39 bytes

import Data.Lists
(transpose.).chunksOf

Note: Data.Lists is from the third-party library lists, which is not on Stackage and hence will not appear on Hoogle.

\$\endgroup\$
  • \$\begingroup\$ Data.Lists doesn't seem to exist. I would assume that you meant Data.List, but it doesn't contain chunksOf. \$\endgroup\$ – Joseph Sible Mar 7 at 0:40
  • \$\begingroup\$ chunksOf only seems to appear with the signature Int -> Text -> [Text].1 \$\endgroup\$ – Sriotchilism O'Zaic Mar 7 at 0:47
  • \$\begingroup\$ @JosephSible, it's in the lists package. \$\endgroup\$ – dfeuer Mar 7 at 0:48
  • \$\begingroup\$ @SriotchilismO'Zaic, lots of things don't show up in Hoogle. It's in the split package and re-exported by the lists package. There are versions of chunksOf for lists, text, sequences, and probably other things. \$\endgroup\$ – dfeuer Mar 7 at 0:50
2
\$\begingroup\$

Kotlin, 53 51 49 bytes

{a,n->(0..n-1).map{a.slice(it..a.size-1 step n)}}

The old, incorrect solution only worked for divisors of the array length. I'm certain this can be golfed down.

Try it online!

\$\endgroup\$
  • \$\begingroup\$ invalid \$\endgroup\$ – ASCII-only Mar 7 at 4:03
  • \$\begingroup\$ Doesn't work when n is not a divisor of the length of the list \$\endgroup\$ – Jo King Mar 7 at 4:04
  • \$\begingroup\$ I see, thanks. Fixing it now \$\endgroup\$ – Adam Mar 7 at 4:08
  • \$\begingroup\$ I believe this is fixed @ASCII-only \$\endgroup\$ – Adam Mar 7 at 4:19
  • 1
    \$\begingroup\$ looks like you can remove the extra pair ot parens \$\endgroup\$ – ASCII-only Mar 7 at 4:43
2
\$\begingroup\$

JavaScript (Node.js), 51 bytes

A=>n=>A.map((x,i)=>e[i%=n]=[...e[i]||[],x],e=[])&&e

Try it online!

JavaScript (Node.js), 53 bytes

A=>n=>g=(i=n)=>i?[...g(--i),A.filter(_=>i--%n==0)]:[]

Try it online!

\$\endgroup\$
1
\$\begingroup\$

APL+WIN 26 or 31 bytes

If individual hands can be represented as columns of a 2D matrix then 26 bytes if an array of arrays then add 5 bytes.

(l,n)⍴((l←⌈(⍴a)÷n)×n←⎕)↑a←⎕

Try it online! ourtesy of Dyalog Classic

or

⊂[1](l,n)⍴((l←⌈(⍴a)÷n)×n←⎕)↑a←⎕

Try it online! Courtesy of Dyalog Classic

Explanation:

a←⎕ prompt for array of cards

((l←⌈(⍴a)÷n)×n←⎕)↑ prompt for integer, pad a with zeros to given even hands

(l,n)⍴ create 2D matrix with each column representing each hand

⊂[1] if required convert to nested vector - APL array of arrays

\$\endgroup\$
1
\$\begingroup\$

TSQL, 44 bytes

-- @       : table containing the input 
-- column c: value of the card, 
-- column a: position on the card in the deck
-- @n      : number of players

DECLARE @ table(a int identity(0,1), c varchar(9))
DECLARE @n int = 4

INSERT @ values('1a'),('2c'),('3e'),('4g'),('5i'),('6k')

SELECT string_agg(c,',')FROM @ GROUP BY a%@n

Try it out

\$\endgroup\$
  • 1
    \$\begingroup\$ Every time I'm on this website I see something new and go "Wow that's impressive, but why?" \$\endgroup\$ – MindSwipe Mar 8 at 7:57
  • \$\begingroup\$ @MindSwipe I have answered a lot of questions on StackOverflow, but many of those questions are the same or almost the same - also it feels like I am working for free. The code-golf questions are different every time and I enjoy it more because I get to use methods I rarely otherwise encounter. \$\endgroup\$ – t-clausen.dk Mar 8 at 8:21
1
\$\begingroup\$

MathGolf, 9 bytes

\ô_í\%q╞;

Try it online!

Explanation

\           swap top elements (pops both input onto stack)
 ô          start block of length 6
  _         duplicate TOS (will duplicate the list)
   í        get total number of iterations of for loop (the other input)
    \       swap top elements
     %      modulo (picks every n:th item of the list
      q     print without newline
       ╞    discard from left of string/array (makes the next player pick cards starting with the next in the deck)
        ;   discard TOS (removes some junk in the end)
\$\endgroup\$
1
\$\begingroup\$

Java (JDK), 90 bytes

A->n->{var o="";for(int h=0,i;h<n;o+="\n")for(i=h++;i<A.length;i+=n)o+=" "+A[i];return o;}

Try it online!

Thanks Olivier Grégoire for the lambda and better incrementing while iterating.

\$\endgroup\$
1
\$\begingroup\$

Ruby, 81 bytes

def s a,n;a.each_with_index.inject(([[]]*n).map(&:dup)){|b,(c,d)|b[d%n]<<c;b};end

Try It Online

\$\endgroup\$
  • 1
    \$\begingroup\$ Could you possibly add a link to an online testing environment for ease of verification? \$\endgroup\$ – Jonathan Frech Mar 8 at 18:05
  • \$\begingroup\$ @JonathanFrech There you go. \$\endgroup\$ – Avilyn Mar 22 at 17:34
  • \$\begingroup\$ Welcome to PPCG! There's a lot of optimizations you can do for length; for example, each_with_index is pretty expensive compared to an incrementing counter, map{[]} basically does the same thing as your map(&:dup) trick, anonymous Proc, etc. that can reduce your code down to 59 bytes. Try it online! Also check out the Ruby tips page \$\endgroup\$ – Value Ink May 14 at 20:19
1
\$\begingroup\$

PHP, 85 83 82 bytes

function($a,$n){while($x<$n)$c[]=array_column(array_chunk($a,$n),+$x++);return$c;}

Try it online!

This will not be the shortest entry, but I thought it'd be fun to try and do it using PHP array function built-ins. Result: long.

Output

1   [1,2,3,4,5,6]   [[1,2,3,4,5,6]]
2   [1,2,3,4,5,6]   [[1,3,5],[2,4,6]]
3   [1,2,3,4,5,6]   [[1,4],[2,5],[3,6]]
4   [1,2,3,4,5,6]   [[1,5],[2,6],[3],[4]]
7   [1,2,3,4,5,6]   [[1],[2],[3],[4],[5],[6],[]]
5   ["9C","QD","2S","4H","6D","AS","9D","TH","5C"]  [["9C","AS"],["QD","9D"],["2S","TH"],["4H","5C"],["6D"]]
\$\endgroup\$
  • 1
    \$\begingroup\$ Just FYI, instead of print_flat you can just do json_encode sandbox - dosn't really change the answer any, just thought I would mention it, cheers! \$\endgroup\$ – ArtisticPhoenix Mar 7 at 20:55
  • \$\begingroup\$ @ArtisticPhoenix well, of course! (facepalm) Thanks! :) \$\endgroup\$ – gwaugh Mar 7 at 21:02
1
\$\begingroup\$

Wolfram Language (Mathematica), 25 bytes

#2[[i;;;;#]]~Table~{i,#}&

Try it online!

\$\endgroup\$
  • \$\begingroup\$ O_o explanation pls \$\endgroup\$ – ASCII-only May 15 at 1:39
  • \$\begingroup\$ @ASCII-only ;; ;; is just a slice, roughly equivalent to python's : :; this gets slices of every \$n\$th element for offsets 1...n \$\endgroup\$ – attinat May 15 at 3:23
  • \$\begingroup\$ oh yeah, forgot it was ;; not ; lol. was looking at this going "wth is i ; ; ; ; #" \$\endgroup\$ – ASCII-only May 15 at 3:51
0
\$\begingroup\$

C# (Visual C# Interactive Compiler), 43 bytes

a=>b=>{int i=0;return a.GroupBy(_=>i++%b);}

Try it online!

\$\endgroup\$
  • \$\begingroup\$ @JoKing [1,2,3], 4 should output [[1],[2],[3]]. You are dealing 3 cards to 4 players. I will update the main question. \$\endgroup\$ – aloisdg Mar 6 at 23:20
  • 1
    \$\begingroup\$ It's generally discouraged to post solutions to your own challenges immediately. \$\endgroup\$ – Shaggy Mar 6 at 23:22
  • 1
    \$\begingroup\$ @Shaggy ok I will take it into account for the next time. It is fine on so and rpg but I guess the competitive aspect of codegolf made it a bit unfair to self post directly. Make sense. \$\endgroup\$ – aloisdg Mar 6 at 23:25
  • \$\begingroup\$ @Joe king you are right! I made a typo :/ \$\endgroup\$ – aloisdg Mar 6 at 23:26
0
\$\begingroup\$

C (gcc), 5 bytes

The compiler flag -Df= (req. leading space) fulfills specification. f(n_cards,n_hands,card_ptr) evaluates to a pointer to a list of hands.

Explanation

In C, it is common practice to implement lists of lists as a single interleaved array, when the number of lists remains constant but all lists can be extended. For example, in this case of dealing cards, it is more common for more cards to get added to each hand than more hands to be added, so it would be reasonable to implement a list of hands as an interleaved list. Coincidentally, the "deck" is such a list, and thus we return the parameter unmodified.

This challenge probably should've been sandboxed.

\$\endgroup\$
  • \$\begingroup\$ I think we all agree for the sandbox \$\endgroup\$ – aloisdg Mar 21 at 8:13
0
\$\begingroup\$

Perl 5 -la, 66 56 bytes

$,=<>;map{push@$_,shift@F}1..$,while@F;say"@$_"for 1..$,

Try it online!

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.