Mastermind: Difference between revisions
Content added Content deleted
No edit summary |
Not a robot (talk | contribs) (Add an APL version) |
||
Line 267: | Line 267: | ||
You won, congratulations! |
You won, congratulations! |
||
</pre> |
</pre> |
||
=={{header|APL}}== |
|||
{{works with|GNU APL}} |
|||
<lang APL>#!/usr/local/bin/apl -s -f -- |
|||
⍝ Define the alphabet |
|||
A←'ABCDEFGHIJKLMNOPQRSTUVWXYZ' |
|||
⍝ Make ASCII values upper case |
|||
∇n←AscUp c |
|||
n←c-32×(c≥97)∧(c≤122) |
|||
∇ |
|||
⍝ Does a list have repeated values? |
|||
∇r←Rpts l |
|||
r←(l⍳l)≢⍳⍴l |
|||
∇ |
|||
⍝ Keyboard input using ⎕ and ⍞ doesn't work well using GNU APL in script mode, |
|||
⍝ so you kind of have to write your own. |
|||
⍝ Read a line of text from the keyboard |
|||
∇l←ReadLine up;k;z;data |
|||
data←'' ⋄ csr←0 ⍝ Start out with empty string and cursor at 0 |
|||
⍝⍝⍝ Keyboard input |
|||
in: k←1⎕fio[41]1 ⍝ Read byte from stdin |
|||
handle: →(k>127)/skip ⍝ Unicode is not supported (Wumpus doesn't need it) |
|||
→(k∊8 127)/back ⍝ Handle backspace |
|||
→(k=10)/done ⍝ Newline = Enter key pressed |
|||
→(k<32)/in ⍝ For simplicity, disregard terminal control entirely |
|||
k←(AscUp⍣up)k ⍝ Make key uppercase if necessary |
|||
z←k⎕fio[42]0 ⍝ Echo key to stdout |
|||
data←data,k ⍝ Insert key into data |
|||
→in ⍝ Go get next key |
|||
⍝⍝⍝ Skip UTF-8 input (read until byte ≤ 127) |
|||
skip: k←1⎕fio[41]1 ⋄ →(k>127)/skip ⋄ →handle |
|||
⍝⍝ Backspace |
|||
back: →(0=⍴data)/in ⍝ If already at beginning, ignore |
|||
z←k⎕fio[42]0 ⍝ Backspace to terminal |
|||
data←¯1↓data ⍝ Remove character |
|||
→in ⍝ Get next key |
|||
⍝⍝ We are done, return the line as text |
|||
done: l←⎕UCS data |
|||
∇ |
|||
⍝ Read a positive number from the keyboard in the range [min...max] |
|||
∇n←min ReadNum max;l;z |
|||
in: l←ReadLine 0 |
|||
z←10⎕fio[42]0 |
|||
→(~l∧.∊'0123456789')/no |
|||
→((min≤n)∧max≥n←⍎l)/0 |
|||
no: ⍞←'Please enter a number between ',(⍕min),' and ',(⍕max),': ' |
|||
→in |
|||
∇ |
|||
⍝ Ask a numeric question |
|||
∇n←q Question lim;min;max |
|||
(min max)←lim |
|||
⍞←q,' [',(⍕min),'..',(⍕max),']? ' |
|||
n←min ReadNum max |
|||
∇ |
|||
⍝ Read a choice from the keyboard |
|||
∇c←Choice cs;ks;k;z |
|||
ks←AscUp ⎕UCS ↑¨cs ⍝ User should press first letter of choice |
|||
in: →(~(k←AscUp 1⎕fio[41]1)∊ks)/in ⍝ Wait for user to make choice |
|||
z←(c←⊃cs[↑ks⍳k])⎕fio[42]0 ⍝ Select and output correspoinding choice |
|||
∇ |
|||
⍝ Ask the user for game parameters |
|||
∇parms←InitGame;clrs;len;gss;rpts |
|||
⎕←'∘∘∘ MASTERMIND ∘∘∘' ⋄ ⎕←'' |
|||
clrs←'How many colors' Question 2 20 |
|||
len←'Code length' Question 4 10 |
|||
gss←'Maximum amount of guesses' Question 7 20 |
|||
⍞←'Allow repeated colors in code (Y/N)? ' |
|||
rpts←'Yes'≡Choice 'Yes' 'No' |
|||
parms←clrs len gss rpts |
|||
∇ |
|||
⍝ Generate a code. |
|||
∇c←rpts MakeCode parms;clrs;len |
|||
(clrs len)←parms |
|||
c←A[(1+rpts)⊃(len?clrs)(?len/clrs)] |
|||
∇ |
|||
⍝ Let user make a guess and handle errors |
|||
∇g←parms Guess code;clrs;rpts;l;right;in |
|||
(clrs rpts num)←parms |
|||
guess: ⍞←'Guess ',(¯2↑⍕num),': ' ⋄ g←ReadLine 1 ⍝ Read a guess from the keyboard |
|||
⍝ Don't count obvously invalid input against the user |
|||
→((⍴code)≢⍴g)/len ⍝ Length is wrong |
|||
→(~g∧.∊A[⍳clrs])/inv ⍝ Invalid code in input |
|||
→((~rpts)∧Rpts g)/rpt ⍝ No repeats allowed |
|||
⍝ Give feedback |
|||
right←g=code ⍝ Colors in right position |
|||
in←g∊code ⍝ Colors not in right position |
|||
fb←(+/right)/'X' ⍝ X = amount of matching ones |
|||
fb←fb,(+/in∧~right)/'O' ⍝ O = amount of non-matching ones |
|||
fb←fb,(+/~in)/'-' ⍝ - = amount of colors not in code |
|||
⍞←' --→ ',fb,⎕UCS 10 |
|||
→0 |
|||
len: ⎕←'Invalid length.' ⋄ →guess |
|||
inv: ⎕←'Invalid color.' ⋄ →guess |
|||
rpt: ⎕←'No repeats allowed.' ⋄ →guess |
|||
∇ |
|||
⍝ Play the game |
|||
∇ Mastermind;clrs;len;gsmax;rpts;code;gs |
|||
⎕rl←(2*32)|×/⎕ts ⍝ initialize random seed |
|||
(clrs len gsmax rpts)←InitGame |
|||
code←rpts MakeCode clrs len |
|||
⎕←2 0⍴'' |
|||
⎕←'The code consists of: ',A[⍳clrs] |
|||
gs←0 |
|||
loop: gs←gs+1 |
|||
→(gs>gsmax)/lose |
|||
→(code≢(clrs rpts gs)Guess code)/loop |
|||
⎕←'○○○ Congratulations! ○○○' |
|||
⎕←'You won in ',(⍕gs),' guesses.' |
|||
→0 |
|||
lose: ⎕←'Alas, you are out of guesses.' |
|||
⎕←'The code was: ',code |
|||
∇ |
|||
Mastermind |
|||
)OFF</lang> |
|||
=={{header|C++}}== |
=={{header|C++}}== |