I am trying to use Racket to make a full deck of playing cards for a BlackJack game. However, I have two problems:
When I use the following code
;This function creates a list of all the card faces.
(define faces '(2 3 4 5 6 7 8 9 10 J Q K A))
;This function creates a list of all card suits.
(define suits '(Clubs Diamonds Hearts Spades))
;make-deck: Creates a new (unshuffled) 52 card deck
; Returns: The deck (a list of cards)
; Parameters: none
(define make-deck
(letrec ([pair-items (lambda (x y)
(cond
[(null? x) '()]
[(null? y) '()]
[(displayln (cons (car x) (cons (car y) (pair-items x (cdr y)))))]
))])
(pair-items faces suits))
)
I get
(2 Spades)
(2 Hearts . #<void>)
(2 Diamonds . #<void>)
(2 Clubs . #<void>)
And I do not know what the issue is.
I have no idea how to reset the iterator
to pair the next element in the faces
function with the whole of the suits
function. Do I use let
?
The trivial way is to use cartesian-product
to generate the list of cards (You can also use for*/list
to iterate over your faces
and suits
lists to get the same effect). Both demonstrated below:
#lang racket/base
(require racket/list)
;This function creates a list of all the card faces.
(define faces '(2 3 4 5 6 7 8 9 10 J Q K A))
;This function creates a list of all card suits.
(define suits '(Clubs Diamonds Hearts Spades))
; These two variables should be equal?
(define deck-1 (cartesian-product faces suits))
(define deck-2 (for*/list ([face (in-list faces)]
[suit (in-list suits)])
(list face suit)))
A big issue with your code is using (cond ... [(displayln ...)])
. displayln
always returns a void value, which, since it's not #f
, is always going to count as true in a cond
. And without a test-body part of that cond-clause, what the true test-expr returns is what the cond
evaluates to, so that's what you're getting added to the lists your function is printing (But not returning). You should probably start by splitting the display of data apart from the creation of it.