Запустите проблему Монти Холла

11

Уже был вопрос об имитации проблемы Монти Холла . Этот другой. Пользователь будет играть на Монти Холла проблемы. Ваша программа сыграет роль ведущего. Монтибот, если хочешь.

Вот шаги:

  1. Выберите (случайным образом), какая из трех дверей скрывает приз.
  2. Выведите визуальный дисплей трех дверей. Простое ABCподойдет. Или три квадрата. Или что угодно.
  3. Получите вход, выбрав одну из дверей. Это может быть щелчок мышью на выбранной двери или ввод одной буквы ( B) или что-то еще.
  4. Откройте другую дверь. Вы не открываете выбранную дверь. Вы не открываете дверь, скрывая главный приз. Это может означать, что у вас нет выбора, или это может означать, что у вас есть выбор из двух. Если у вас есть выбор из двух, выберите один наугад. Визуально укажите, что дверь была открыта и за ней не было спрятано ни одного приза. Для программного ввода / вывода на основе текста это может быть так же просто, как вывод AB0, чтобы показать, что дверь Cбыла открыта. Не стесняйтесь быть более изобретательным. Если вы делаете программу с графическим интерфейсом, ваш выбор дисплея остается за вами.
  5. Принять ввод от пользователя. Пользователь может вводить stickили switch(или, для программы с графическим интерфейсом, нажимать на кнопки, или использовать выборочный ввод, или что-то еще). Если пользователь вводит что-либо кроме stickили switch, реализация не определена. Делай что хочешь.
  6. Вывести текст You won!или You lost.
  7. Прекратить программу.

Правила:

  1. Когда вам нужно что-то выбрать случайно , не беспокойтесь о случайной криптографии. Подойдет любая rand()функция.
  2. Программа не должна обманывать. Приз должен быть на месте до начала игры. То есть, шаги должны быть выполнены в указанном порядке: сначала выберите дверь, за которой нужно спрятать свой приз, затем попросите игрока выбрать. Выбор, какую дверь открыть на шаге 4, должен произойти на шаге 4: она не выбрана заранее.
  3. Вывод на шаге 6 должен быть честным.
  4. Это код гольф. Самый короткий код выигрывает.
наряжать
источник
Я впервые публикую на этом сайте, но я много скрываюсь, поэтому я думаю, что я знаком с вашими нормами.
TRiG
На meta.codegolf.stackexchange.com есть ветка для предложения вопросов и разрешения людям решать любые проблемы до того, как они будут официально опубликованы. Я не знаю, есть ли здесь что-то конкретно не так, что могло бы быть сглажено, но это может быть полезно знать в следующий раз.
подземная
Я ожидаю, что победителем станет еще один ответ на сценарий в гольфе ...
Виктор Стафуса
1
Кстати, «изобретательность» плохо сочетается с игрой в гольф, поскольку изобретательность потребляет несколько байтов, а цель игры в гольф противоположна этому.
Виктор Стафуса
Да, @Victor. Быть изобретательным не обязательно. Я просто (а) не хотел ограничивать это программами командной строки, и (б) понятия не имел, как программа без командной строки должна реализовывать выбор пользователя. Так что я оставил это до ответчиков. Быть изобретательным - это вариант, но он не наберет лишних очков.
TRiG

Ответы:

2

APL, 77

p←?3⋄d[e[?⍴e←(⍳3)~p,c←⍞⍳⍨⎕←d←3↑⎕A]]←'_'⋄⎕←d⋄⎕←'You','lost' 'won!'[(c=p)=5=⍴⍞]

Потребности ⎕IO←0. Проверено на Dyalog.

объяснение

p←?3                       ⍝ p(rize) is a random number between 1 and 3
⎕←d←3↑⎕A                   ⍝ d(oors) is the string 'ABC'; output it
c←d⍳⍞                      ⍝ ask for one of the letters; c(hoice) is its position
o←e[?⍴e←(⍳3)~p,c]          ⍝ o(pen) is a random position except for p and c
d[o]←'_'                   ⍝ replace the o position in the d string with a '_'
⎕←d                        ⍝ output the modified d string
w←(c=p)=5=⍴⍞               ⍝ get choice, if it's stick (5 chars) and c=p, or neither, (w)in 
⎕←'You','lost' 'won!'[w]   ⍝ print the result

Примеры

      p←?3⋄d[e[?⍴e←(⍳3)~p,c←⍞⍳⍨⎕←d←3↑⎕A]]←'_'⋄⎕←d⋄⎕←'You','lost' 'won!'[(c=p)=5=⍴⍞]
ABC
A
AB_
stick
You lost 
      p←?3⋄d[e[?⍴e←(⍳3)~p,c←⍞⍳⍨⎕←d←3↑⎕A]]←'_'⋄⎕←d⋄⎕←'You','lost' 'won!'[(c=p)=5=⍴⍞]
ABC
A
AB_
stick
You won! 
Тобия
источник
Прекрасный! Но я думаю, что в источнике есть мутирование =в объяснение.
TRiG
Спасибо, это была опечатка, последняя ошибка, которую я исправил перед публикацией.
Tobia
2

Питон, 157

from random import*
C=choice
I=raw_input
p='\n> '
a='ABC'
g=C(a)
i=I(a+p)
print'You '+'lwoosnt!'[(i==g)^('w'in I(a.replace(C(list(set(a)-{g,i})),'_')+p))::2]

Пример:

$ python monty.py
ABC
> A
AB_
> switch
You won!
GRC
источник
2

PowerShell: 192 174

Отличия от оригинала:

  • -8 символов Поскольку визуальное отображение дверей может быть «любым», я понял, что могу сохранить некоторые символы (в частности, апострофы, необходимые для определения строк), используя цифры вместо букв.
  • -8 символов Выбирая однозначные простые числа для представления дверей, я мог использовать более короткий оператор по модулю вместо фактического оператора сравнения, когда мне нужно было сопоставить двери, чтобы выяснить возможные варианты выбора хоста или обмен дверями игрока. ( Кратко объяснено здесь. )
  • -2 персонажа Обмен местами ответов о победе / поражении в последнем утверждении if / else позволил мне также использовать трюк по модулю.

Гольф-код

$w=($d=3,5,7)|random;357;$p=read-host;-join$d-replace($h=$d|?{$_%$w-and$_%$p}|random),0;if((read-host)-match'w'){$p=$d|?{$_%$p-and$_%$h}}if($p%$w){'You lost'}else{'You won!'}

Un-Golfed код с комментариями

# Set up an array of doors ($d), and choose one to be the winner ($w).
$w=($d=3,5,7)|random;

# Show doors.
357;

# Get input and save player's choice ($p).
$p=read-host;

# Join the doors into one string, replacing the host's choice ($h) with a zero, and display them again.
-join$d-replace
(
    # Host will randomly choose a door from those which are not evenly divisible by $w or $p.
    $h=$d|?{$_%$w-and$_%$p}|random
 ),0;

# Get input from player. If it contains a 'w', switch doors.
# While this is generally a sloppy way to distinguish 'switch' from 'stick', it is allowed by the rules.
# "If the user enters anything other than stick or switch, the implementation is undefined. Do whatever you want."
if((read-host)-match'w')
{
    # Player will switch doors to one which is not evenly divisible by the $h or the original $p.
    $p=$d|?{$_%$p-and$_%$h}
}

# Announce the result.
# If $p is not evenly divisible by $w, player has lost. Otherwise, they have won.
if($p%$w){'You lost'}else{'You won!'}

# Variables cleanup - not included in golfed code.
rv w,d,p,h
Iszi
источник
Мне нравится, если он содержит трюк "W" .
TRiG
Между прочим, я первоначально сказал, что если ввод был чем-то отличным от «stick» или «switch», программа должна завершиться, но я передумал перед публикацией.
TRiG
@TRiG Спасибо за это. Хотя это не было бы трудно реализовать, это добавило бы немного вздутия.
Изи
В любом случае, различные трюки (ваше обнаружение или подсчет символов ) более интересны.
TRiG
0

Javascript, 221 197

(function(q,r,s,t,u,v){f='ABC';d=[0,1,2];b=q()%3;a=r(f);d.splice(a,1);(a==b)?(r(f[d[q()%2]])==t)?s(u):s(v):(r(f[d[(d[0]==b)+0]])!=t)?s(u):s(v)})(Date.now,prompt,alert,'stick','You won!','You lost')

Он использует два вызова Date.now () для случайности с подсказкой между ними, чтобы гарантировать задержку. Пользовательский ввод - это индекс на основе 0 (правило говорило «что угодно»). Следующее предупреждение говорит, какая дверь была открыта. Вот немного более длинная версия, которая дает ответ до того, как пользователь выберет, чтобы убедиться, что он не обманывает:

(function(q,r,s,t,u,v){f='ABC';d=[0,1,2];b=q()%3;s('ans:'+b);a=r(f);d.splice(a,1);(a==b)?(r(f[d[q()%2]])==t)?s(u):s(v):(r(f[d[(d[0]==b)+0]])!=t)?s(u):s(v)})(Date.now,prompt,alert,'stick','You won!','You lost')

Скрипка: http://jsfiddle.net/acbabis/9J2kP/

РЕДАКТИРОВАТЬ: Спасибо, Дейв

aebabis
источник
Вы можете сократить его до 197: (function(q,r,s,t,u,v){f='ABC';d=[0,1,2];b=q%3;a=r(f);d.splice(a,1);(a==b)?((r(f[d[q%2]])==t)?s(u):s(v)):(r(f[d[(d[0]==b)+0]])!=t)?s(u):s(v)})(Date.now(),prompt,alert,'stick','You won!','You lost')
Дейв
@dave Это полезно. Я не думал использовать здесь троичный оператор. Я не могу передать Date.now (), хотя, потому что случайные числа должны быть независимыми. Я могу, однако, передать Date.now.
aebabis
@acbabis "I can't pass Date.now() ... I can, however, pass Date.now"???
Timtech
@Timtech date.nowпередает функцию, date.now()передает результат функции
dave
@ Дэйв О, я понял. Спасибо :)
Timtech
0

PHP> = 5,4, 195 192

$r=[0,1,2];unset($r[$p=rand(0,2)]);$d='012';echo"$d\n";fscanf(STDIN,"%d",$c);unset($r[$c]);$d[array_rand($r)]='_';echo"$d\n",!fscanf(STDIN,"%s",$s),'You '.($s=='switch'^$c==$p?'won!':'lost.');

Выход:

012
1
01_
stick
You won!
Достойный Дилетант
источник