diff options
author | elioat <elioat@tilde.institute> | 2023-08-23 07:52:19 -0400 |
---|---|---|
committer | elioat <elioat@tilde.institute> | 2023-08-23 07:52:19 -0400 |
commit | 562a9a52d599d9a05f871404050968a5fd282640 (patch) | |
tree | 7d3305c1252c043bfe246ccc7deff0056aa6b5ab /js/games/nluqo.github.io/~bh/ssch9/bridge | |
parent | 5d012c6c011a9dedf7d0a098e456206244eb5a0f (diff) | |
download | tour-562a9a52d599d9a05f871404050968a5fd282640.tar.gz |
*
Diffstat (limited to 'js/games/nluqo.github.io/~bh/ssch9/bridge')
-rw-r--r-- | js/games/nluqo.github.io/~bh/ssch9/bridge | 254 |
1 files changed, 254 insertions, 0 deletions
diff --git a/js/games/nluqo.github.io/~bh/ssch9/bridge b/js/games/nluqo.github.io/~bh/ssch9/bridge new file mode 100644 index 0000000..6d4cede --- /dev/null +++ b/js/games/nluqo.github.io/~bh/ssch9/bridge @@ -0,0 +1,254 @@ +\input bkmacs +\projchap{Project: Scoring Bridge Hands} +\write\toc{\begingroup\blskip{1}} %%% ends in leap.tex + +At the beginning of a game of bridge, each player assigns a value to his or +her hand by counting {\it points.\/} Bridge players use these points in the +first part of the game, the ``bidding,'' to decide how high to bid. (A +bid is a promise about how well you'll do in the rest of the game. If you +succeed in meeting your bid you win, and if you don't meet the bid, you +lose.) For example, if you have fewer than six points, you generally don't +bid anything at all. + +You're going to write a computer program to look at a bridge hand and decide +how many points it's worth. You won't have to know anything about the rest +of the game; we'll tell you the rules for counting points. + +A bridge hand contains thirteen cards. Each ace in the hand is worth four +\justidx{bridge points} +\justidx{points, bridge} +points, each king is worth three points, each queen two points, and each +jack one. The other cards, twos through tens, have no point value. +So if your hand has two aces, a king, two jacks, and eight other +cards, it's worth thirteen points. + +A bridge hand might also have some ``distribution'' points, which are points +having to do with the distribution of the thirteen cards among the four +suits. If your hand has only two cards of a particular suit, then it is +worth an extra point. If it has a ``singleton,'' only one card of a +particular suit, that's worth two extra points. A ``void,'' no cards in a +particular suit, is worth three points. + +In our program, we'll represent a card by a word like {\tt h5} (five of +hearts) or {\tt dk} (king of diamonds).\footnt{Why not {\tt 5h}? Scheme +words that begin with a digit but aren't numbers have to be surrounded with +double-quote marks. Putting the suit first avoids that.} A hand will be a +sentence of cards, like this: + +{\prgex% +(sa s10 s7 s6 s2 hq hj h9 ck c4 dk d9 d3) +} + +This hand is worth 14 points:\ ace of spades (4), plus queen of hearts +(2), plus jack of hearts (1), plus king of clubs (3), plus king of diamonds +(3), plus one more for having only two clubs. + +To find the suit of a card, we take its {\tt first}, and to find the rank, we +take the {\tt butfirst}. (Why not the {\tt last}?) + +We have a particular program structure in mind. We'll describe all of the +procedures you need to write; if you turn each description into a working +procedure, then you should have a complete program. In writing each +procedure, take advantage of the ones you've already written. Our +descriptions are ordered {\it \idx{bottom-up}\/}, which means that for each +procedure you will already have written the helper procedures you need. +(This ordering will help you write the project, but it means that we're +beginning with small details. If we were describing a project to help you +understand its structure, we'd do it in {\it \idx{top-down}\/} order, +starting with the most general procedures. We'll do that in the next +chapter, in which we present a tic-tac-toe program as a larger Scheme +programming example.) + +\function{Card-val} + +Write a procedure {\tt \ufun{card-val}} that takes a single card as its +argument and returns the value of that card. + +{\prgex% +> (card-val 'cq) +2 + +> (card-val 's7) +0 + +> (card-val 'ha) +4 +} + +\solution +{\prgex% +(define (card-val card) + (cond ((equal? (bf card) 'a) 4) + ((equal? (bf card) 'k) 3) + ((equal? (bf card) 'q) 2) + ((equal? (bf card) 'j) 1) + (else 0))) +} +@ + +\function{High-card-points} + +Write a procedure {\tt \ufun{high-card-points}} that takes a hand as its +argument and returns the total number of points from high cards in the +hand. (This procedure does {\it not\/} count distribution points.) + +{\prgex% +> (high-card-points '(sa s10 hq ck c4)) +9 + +> (high-card-points '(sa s10 s7 s6 s2 hq hj h9 ck c4 dk d9 d3)) +13 +} + +\solution +{\prgex% +(define (high-card-points hand) + (accumulate + (every card-val hand))) +} +@ + +\function{Count-suit} + +Write a procedure {\tt \ufun{count-suit}} that takes a suit and a hand as +arguments and returns the number of cards in the hand with the given suit. + +{\prgex% +> (count-suit 's '(sa s10 hq ck c4)) +2 + +> (count-suit 'c '(sa s10 s7 s6 s2 hq hj h9 ck c4 dk d9 d3)) +2 + +> (count-suit 'd '(h3 d7 sk s3 c10 dq d8 s9 s4 d10 c7 d4 s2)) +5 +} + +\solution +{\prgex% +(define (count-suit suit hand) + (count (keep (lambda (card) (equal? (first card) suit)) hand))) +} + +Thinking about domain and range really helps in this problem; +there are many ways to get confused about what to use as argument +to which helper function. In particular, it's important to +distinguish among the data types suit, card, and hand. +@ + +\function{Suit-counts} + +Write a procedure {\tt \ufun{suit-counts}} that takes a hand as its argument +and returns a sentence containing the number of spades, the number of hearts, +the number of clubs, and the number of diamonds in the hand. + +{\prgex% +> (suit-counts '(sa s10 hq ck c4)) +(2 1 2 0) + +> (suit-counts '(sa s10 s7 s6 s2 hq hj h9 ck c4 dk d9 d3)) +(5 3 2 3) + +> (suit-counts '(h3 d7 sk s3 c10 dq d8 s9 s4 d10 c7 d4 s2)) +(5 1 2 5) +} + +\solution +{\prgex% +(define (suit-counts hand) + (every (lambda (suit) (count-suit suit hand)) + '(s h c d))) +} + +This solution is not obvious, because the second argument to +{\tt every} is a constant, rather than one of the original +arguments. Students may find it easier to understand this +less elegant alternative: + +{\prgex% +(define (suit-counts hand) + (se (count-suit 's hand) + (count-suit 'h hand) + (count-suit 'c hand) + (count-suit 'd hand))) +} +@ + +\function{Suit-dist-points} + +Write {\tt \ufun{suit-dist-points}} that takes a number as its argument, +interpreting it as the number of cards in a suit. The procedure should +return the number of distribution points your hand gets for having that +number of cards in a particular suit. + +{\prgex% +> (suit-dist-points 2) +1 + +> (suit-dist-points 7) +0 + +> (suit-dist-points 0) +3 +} + +\solution +{\prgex% +(define (suit-dist-points n) + (if (<= n 2) + (- 3 n) + 0)) +} + +\noindent or, the slightly less elegant way: + +{\prgex% +(define (suit-dist-points n) + (cond ((= n 0) 3) + ((= n 1) 2) + ((= n 2) 1) + (else 0))) +} +@ + +\function{Hand-dist-points} + +Write {\tt \ufun{hand-dist-points}}, which takes a hand as its argument and +returns the number of distribution points the hand is worth. + +{\prgex% +> (hand-dist-points '(sa s10 s7 s6 s2 hq hj h9 ck c4 dk d9 d3)) +1 + +> (hand-dist-points '(h3 d7 sk s3 c10 dq d8 s9 s4 d10 c7 d4 s2)) +3 +} + +\solution +{\prgex% +(define (hand-dist-points hand) + (accumulate + (every suit-dist-points (suit-counts hand)))) +} +@ + +\function{Bridge-val} + +Write a procedure {\tt \ufun{bridge-val}} that takes a hand as its argument +and returns the total number of points that the hand is worth. + +{\prgex% +> (bridge-val '(sa s10 s7 s6 s2 hq hj h9 ck c4 dk d9 d3)) +14 + +> (bridge-val '(h3 d7 sk s3 c10 dq d8 s9 s4 d10 c7 d4 s2)) +8 +} + +\solution +{\prgex% +(define (bridge-val hand) + (+ (high-card-points hand) + (hand-dist-points hand))) +} +@ + +\bye |