Гольф wordgame гольф


14

Натхненний reddit .

Напишіть програму, яка грає Hangman .

  • Програма вибирає випадкове слово зі списку N слів, де N> 2.
  • Список слів можна надати програмі будь-яким обраним вами способом.
  • При кожній ітерації

    • Роздрукуйте стан гри, використовуючи підкреслення для ще не виявлених букв:

    H _ N _ _ _ N

    • Роздрукуйте кількість спроб, що залишилися

    10

    • Прочитайте лист від stdin та оновлюйте стан гри, віднімаючи спробу, якщо вони здогадаються про неправильну букву.

    A (вхід)

    H A N _ _ A N

    10

    • Повторюйте, поки всі букви не здогадаються або спроби не досягне 0
  • Використовуйте будь-яку мову
  • Виграє найменша кількість символів.
  • Малювати шибеницю не обов’язково, але ви заробите заробітки та кудо.

Чи можу я дозволити кожному слову в списку однакову кількість символів?
Пітер Олсон

Чи повинні букви на виході розділяти пробілами?
Lowjacker

@Peter Of The Corn: слід припустити, що список слів є довільним
drspod

@Lowjacker: пробіли покращують розбірливість послідовних підкреслень, інакше важко порахувати, скільки букв вони представляють.
drspod

Відповіді:


6

Рубін 1,9, 134 132 120 117 108 107

Список слів, наданий в ARGV. Слова та введені літери повинні відповідати у випадку.

r=w=$*.sample
t=10
loop{puts [*w.tr(r,?_).chars]*' ',t
t>0&&r>''?w[l=STDIN.gets[0]]?r=r.tr(l,''):t-=1:exit}

8

Дарн, я вважав, що це означає, що "перемагає найменша кількість ліній". Я не збираюсь вигравати тут жодних найменших конкурсів персонажів, але ця програма Common Lisp - це лише один рядок.

(let ((words (list "that" "help" "rent" "chair" "octopus" "monitor" "manual" "speakers" "onomatopoeia" "regardless" "irresponsible" "cornerstone"))) (let ((word (nth (random (length words)) words))) (format t "~a~%" (funcall (defun play (word current remaining-attempts) (progn (if (not (find #\_ current)) (return-from play "You win!")) (if (equalp remaining-attempts 0) (return-from play "You lose!")) (format t "~a~%~d~%" current remaining-attempts) (let ((guess (char (read-line) 0)) (index 0) (found nil)) (loop for letter across word do (if (equalp guess letter) (progn (setf (char current index) letter) (setf found t))) (setf   index (+ index 1))) (if found (play word current remaining-attempts) (play word current (- remaining-attempts 1)))))) word (map 'string #'(lambda (c) #\_) word) 10))))

1
Я вітаю вас, тому що я майже впевнений, що ви навмисно жартуєте :-)
Доктор Біль

8

Пітон 3.

from random,sys import *
w=choice(*argv)
L=set(w)
a=10
while L and a:
 print(" ".join("_"if x in L else x for x in w),a)
 try:L-=set(input()[0])
 except:a-=1

Хоча я вважаю за краще цей: довше, але приємніше.

import random
w=random.choice(list(open("/usr/dict/words")))[:-1]
L=set(w)
a=10
while L and a:
 print(" ".join("_"if x in L else x for x in w),a)
 try:L.remove(input()[0])
 except:a-=1
print w

Якщо мені не довелося також друкувати a, я міг би використати *двічі:print(*("_"if x in L else x for x in w))
badp

4

c ++ (-головок)

struct h{h(char a):b(a){}char operator()(char c,char d){return d!='_'?d:c==b?c:'_';}char b;};

int main(int a,char**b){
srand(time(0));string c=*(b+rand()%(a-1)+1),d(c.size(),'_'),e;
char f=10,g;
while(f){
cout<<"> ";cin>>g;e=d;
transform(c.begin(),c.end(),d.begin(),d.begin(),h(g));if(e==d)--f;
cout<<d<<endl<<(int)f<<endl;if(d==c)break;
}return 0;}

кішка / usr / dict / слова | xargs вішалка


Запрошення для введення ">" не потрібно для рішення, я просто додав його у запитання, щоб вказати, що воно було введено, оскільки багато мов надають такий підказки, як цей.
drspod

@drspod Тоді слід відредагувати це питання, щоб відобразити це.
Lowjacker

відредаговано для уточнення
drspod

2

Пітон

import random

DEFAULT_ATTEMPTS = 10

def print_word(word, uncovered):
    for c in word:
        if c not in uncovered:
            c = '_'
        print c,
    print ''

def get_letter():
    letter = None
    while letter is None:
        letter = raw_input('> ')
        if len(letter) != 1:
            print 'Letters must be 1 character.  Try again.'
            letter = None
    return letter

if __name__ == '__main__':
    import sys

    if len(sys.argv) != 2: sys.exit(1)
    with open(sys.argv[1], 'r') as f:
        words = [word.strip() for word in f.readlines() if word.strip()]

    word = random.choice(words)
    uncovered = set([' '])
    attempts = DEFAULT_ATTEMPTS

    while attempts > 0 and any(letter not in uncovered for letter in word):
        print_word(word, uncovered)
        print attempts

        letter = get_letter()
        if letter in uncovered:
            print 'You have already tried that letter.'
        elif letter in word:
            print 'You got it!'
        else:
            print 'Wrong!'
            attempts -= 1

        uncovered.add(letter)

    if attempts == 0:
        print 'You lose!',
    else:
        print 'You win!'
    print 'The phrase was "%s".' % word

Я не дуже намагався за найменших персонажів, просто хотів зробити це якомога менше, не жертвуючи нічого.


@user: Можливо, вас зацікавить чудовий сценарій користувача Джорджа Едісона для цього сайту, який ставить ваш код (як скопійований тут badp) на 1225 символів.
dmckee --- кошеня колишнього модератора

Я думаю, що саме тому я використовував вкладки, і вони були перетворені на пробіли тут. wc каже, що це 1034 з вкладками.
Сергій Г


2

Perl, 112 char. Я відчуваю, що можу зробити краще - можливо, спробую знову

$_=$ARGV[rand@ARGV];$a=10;while($a&&/[a-z]/){print map/[A-Z]/?$_:'_',split'';$x=<STDIN>;chop$x;s/$x/$x/ig||$a--}

Слова наводяться в командному рядку, літери набрані великим регістром


Вниз до 107 $_=$ARGV[rand@ARGV];$a=10;while($a&&/[a-z]/){$y=$_;$y=~y/a-z/_/;print$y;$x=<STDIN>;chop$x;s/$x/$x/ig||$a--}

3
Ви можете просто відредагувати оригінальну відповідь.
Lowjacker

1
Це не відображає кількість решти спроб.
Lowjacker

2

Clojure

Це 400 байт gzipped, що ще досить багато, ймовірно, через те, як Clojure обробляє стан, що змінюється.

(def m ["will" "work" "for" "food"])
(def w (nth m (rand-int (count m))))
(def *s* (atom (replicate (count w) "_")))
(def *a* (atom 10))

(defn g [s a]
  (str (apply str (interpose " " s)) "\n" a))

(loop [n (read-line)]
  (if (some (set n) w)
    (swap! *s* (fn [s]
                 (map 
                   (fn [i]
                     (if (= n (str (nth w i)))
                       n
                       (nth s i)))
                   (range 0 (count s)))))
    (swap! *a* dec))

  (println (g (deref *s*) (deref *a*))) 

  (if (and (< 0 (deref *a*)) (some #{"_"} (deref *s*)))
    (recur (read-line))))

2

C # 370

using System;namespace h{class P{static void Main(string[]a){int c=10,d,l;char y=' ';string w=a[new Random().Next(a.Length)];l=w.Length;char[]x=new char[l];for(d=-1;++d<l;x[d]='-');while(c>0){for(d=-1;++d<l;x[d]=(y==w[d]||x[d]!='-')?w[d]:x[d]);Console.WriteLine(new string(x)+" "+c);if(w==new string(x))return;y=Console.ReadKey(true).KeyChar;if(!w.Contains(y+""))c--;}}}

список слів як аргумент


1

VB.NET


Я ще не намагався його зменшити, але:
Перше зменшення:
Друге скорочення (3759 символів):

Module Hangman
    Sub Main()
        Dim m As Int32, w = "banana|apple|pear|dog|cat|orange|monkey|programming|hangman".Split("|")(New Random().Next(9)), g = "", e = "", x, c As Char, f As Boolean, r = Sub(z) Console.Write(z), p = Sub(y, h) Console.SetCursorPosition(y, h), a = Sub() Console.Clear(), q = Function() Console.ReadKey(1), d = Sub()
                                                                                                                                                                                                                                                                                                                          r("       +--------+S       |        |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S                |S   ---------------------".Replace("S", vbCrLf))
                                                                                                                                                                                                                                                                                                                          p(0, 2)
                                                                                                                                                                                                                                                                                                                          r(String.Join(vbCrLf, "    /------\S    | O   O|S    \  ... /S     ------ S        |   S        |   S        |   S        |   S -------+-------S        |   S        |   S        |   S       / \  S      /   \  S     /     \  S    /       \  ".Split("S").Take(m * 4)))
                                                                                                                                                                                                                                                                                                                      End Sub
        Console.CursorVisible = 0
        Do
            a()
            d()
            p(30, 10)
            f = 0
            For Each x In w
                If g.Contains(x) Then
                    r(x)
                Else
                    r(" ")
                    f = 1
                End If
                Console.CursorTop += 1
                Console.CursorLeft -= 1
                r("_")
                Console.CursorTop -= 1
                r(" ")
            Next
            If Not f Then
                a()
                d()
                p(30, 10)
                r("You win! Press any key to close.")
                q()
                End
            End If
            p(30, 13)
            r(e)
            Do
                c = q().KeyChar
            Loop Until Char.IsLetter(c)
            If g.Contains(c) Then
                e = "You have already guessed that letter."
            Else
                g &= c
                If w.Contains(c) Then
                    e = "There is a" & If("aehilmnorsx".Contains(c), "n", "") & " """ & c & """ in the word."
                Else
                    e = "There is no """ & c & """ in the word. Try again."
                    m += 1
                End If
            End If
        Loop Until m = 4
        a()
        d()
        p(30, 10)
        r("You lose! Press any key to close.")
        q()
    End Sub
End Module

Чи справді потрібні всі відступи?
Lowjacker

це полегшує читання, чи не так?
Нейт Коппенгавер

Як у блоках? Ні, це не потрібно, але я не вважаю це персонажами.
Ри-

0

Powershell, 125 байт

$w=$h=$args|random|% t*y
for($n=10){$w-replace"[ $h]",'_'-join' ';$n
if(!$h+!$n){break}$n-=($c=Read-Host)-notin$h
$h=$h-ne$c}

Менш тестовий сценарій для гольфу:

$f = {

$word=$hidden=$args|random|% toCharArray    # let $word and $hidden are a random word chars
#$word                                      # uncomment this to cheating
for($n=10){                                 # forever for with init section
    $word-replace"[ $hidden]",'_'-join' '   # display the word with hidden letters
    $n                                      # display $n
    if(!$hidden+!$n){break}                 # break loop if hidden array is empty or n equal to 0
    $n-=($c=Read-Host)-notin$hidden         # input $c from user, decrease $n if $c does not in $hidden array
    $hidden=$hidden-ne$c                    # recreate $hidden array with removed $c
}

}

$words = gc .\wordlist.txt
&$f $words

Приклад виходу, коли гравець, який здогадується, програв :

_ _ _ _ _ _ _ _
10
i
_ _ _ _ _ _ _ _
9
e
_ _ e _ _ _ _ e
9
o
o _ e _ _ o _ e
9
a
o _ e _ _ o _ e
8
q
o _ e _ _ o _ e
7
q
o _ e _ _ o _ e
6
q
o _ e _ _ o _ e
5
q
o _ e _ _ o _ e
4
q
o _ e _ _ o _ e
3
q
o _ e _ _ o _ e
2
q
o _ e _ _ o _ e
1
q
o _ e _ _ o _ e
0

Приклад результату, коли гравець, який здогадується, виграв :

_ _ _ _ _ _ _ _ _ _
10
e
_ _ _ _ e _ _ _ _ _
10
o
_ o _ _ e _ _ _ _ _
10
i
_ o _ _ e _ _ i _ _
10
a
_ o _ _ e _ _ i a _
10
l
_ o _ _ e _ _ i a l
10
c
c o _ _ e _ c i a l
10
m
c o m m e _ c i a l
10
t
c o m m e _ c i a l
9
r
c o m m e r c i a l
9
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.