gehacktes /// noniq.at

0005Ist der 50:50-Joker ein Ziegenproblem?

Ob Wahrscheinlichkeitsrechnung bei der Millionenshow hilft – und wie man das mit einem kleinen Ruby-Programm herausfinden kann.

Vom Ziegenproblem habt ihr vermutlich schon gehört (falls nicht: schnell nachlesen). Dazu folgendes Gedankenexperiment:

Ich bin Kandidat bei der Millionenshow1. Es kommt eine Frage, bei der ich keine Ahnung hab, welche Antwort richtig sein könnte. Ich suche mir also rein zufällig eine der Antworten aus – sagen wir „A“.

Jetzt fällt mir ein, dass ich den 50:50-Joker noch nicht verwendet hab. Ich setze den Joker ein, und die Antworten C und D fallen weg, A und B bleiben übrig.

Soll ich meine ursprüngliche Wahl (A) jetzt beibehalten, oder zu B wechseln?

Beim Ziegenproblem ist Wechseln die bessere Strategie. Gilt das auch für die Millionenshow – zumindest für jene Fälle, wo ich wie beschrieben keine Ahnung habe, den 50:50-Joker verwende und die ursprünglich ausgesuchte Antwort nach dem Joker noch da steht?

Genau diese Frage wird aktuell auf Kritisch gedacht heiß diskutiert. Ich hab ein kleines Ruby-Programm geschrieben, dass dieses Problem simuliert:

num_rounds = 10000
answers    = %W(A B C D)
strategies = %W(STAY CHANGE)

# Helfermethode und Alias für bessere Lesbarkeit
class Array
  def except(element)
    self - [element]
  end
  alias choose_randomly sample
end

strategies.each do |strategy|
  num_successes      = 0
  num_skipped_rounds = 0

  num_rounds.times do
    correct_answer = answers.choose_randomly
    initial_choice = answers.choose_randomly
    joker_result   = [correct_answer, answers.except(correct_answer).choose_randomly].sort

    if joker_result.include?(initial_choice)
      final_choice = if strategy == "CHANGE"
        joker_result.except(initial_choice).first
      else
        initial_choice
      end
      success = final_choice == correct_answer
      num_successes += 1 if success
      # puts "#{correct_answer} : #{initial_choice} - #{joker_result.join(' ')} - #{final_choice} : #{success}"
    else
      # puts "#{correct_answer}  : #{initial_choice} - #{joker_result.join(' ')} - SKIPPED"
      num_skipped_rounds += 1
    end
  end

  num_relevant_rounds = num_rounds - num_skipped_rounds
  puts "#{strategy}, #{num_relevant_rounds} relevant rounds (= %.1f%%)" % (num_relevant_rounds * 100.0 / num_rounds)
  puts "#{num_successes} successes (= %.1f%%)" % (num_successes * 100.0 / num_relevant_rounds)
  puts
end

Der Code ist, hoffe ich, weitestgehend selbsterklärend2: Ich simuliere 10.000 Runden – zuerst mit der Strategie „STAY“ (Antwort nicht wechseln), dann mit der Strategie „CHANGE“ (Antwort wechseln). In jeder Runde wird zufällig festgelegt, welche Antwort richtig ist und welche ich mir am Anfang aussuche. Danach wird, ebenfalls zufällig, das Jokerergebnis festgelegt – also welche beiden Antworten stehen bleiben. Falls die ursprünglich gewählte Antwort nicht dabei ist, wird diese Runde ignoriert, ansonsten wird entsprechend der Strategie entweder die ursprüngliche Antwort beibehalten oder eben gewechselt. Am Schluss wird für jede Strategie ausgegeben, wie oft die richtige Antwort erraten wurde.

Das Ergebnis verrat ich noch nicht – wer will, kann sich hier (SPOILER!) das Ergebnis3 anschauen.


  1. Für die Nicht-ÖstereicherInnen unter euch: Das ist die österreichische Version von „Wer wird Millionär?“. 

  2. Ich mag Ruby ja sowieso, aber gerade für solche Aufgaben find ich's besonders gut geeignet – der resultierende Code liest sich einfach schön. 

  3. Bzw. ein Ergebnis – aufgrund der Zufallszahlen ist das konkrete Ergebnis bei jedem Durchlauf ein anderes. Aber die Größenordnungen sind natürlich immer dieselben. 



0004Klingelblink im TischtenniskellerBLITZbot15’s journey around CCCamp15 (part 1)0006