The Monty Hall problem

Arjen Markus (21 june 2017) Here is a small program to simulate the so-called Monty Hall problem , one of those fascinating counter-intuitive results in statistics and probabilistics. While it is not really difficult to describe the set-up, simulating it turned out to be a trifle tricky. But the outcome is in agreement with the theoretical results.

Note: it could be done in fewer lines as well.

# threedoors.tcl --
#     Simulate a classical game show problem:
#     - Three doors are shown, one gives access to the prize
#     - You chose a door
#     - The game show host shows that one of the other doors
#       does NOT contain the prize and asks you if you want
#       to change your mind
#
#     The statistically correct answer is: you should change your
#     mind. It is counter-intuitive though that this should matter.
#
#     This is a demonstration of the situation.
#

set trials        10000
#set trials        3
set otherDoorWins 0
set firstDoorWins 0

for {set i 0} {$i < $trials} {incr i} {
    # Determine the winning door
    set winning [expr {int(3 * rand())}]

    # Select a door
    set selected [expr {int(3 * rand())}]

    # Now exclude a non-winning door
    set excludables {}
    foreach door {0 1 2} {
        if { $door != $selected } {
            lappend excludables $door
        }
    }

    #puts "Selected:  $selected"
    #puts "Winning:   $winning"
    #puts "Excluding: $excludables"

    set excludedIndex [expr {int(2 * rand())}]
    if { [lindex $excludables $excludedIndex] == $winning } {
        set excludedIndex [expr {1 - $excludedIndex}]
    }

    set remaining [lindex $excludables [expr {1 - $excludedIndex}]]

    #puts "Remaining: $remaining"

    # Check if we have won the prize or if the remaining door is the one
    if { $winning == $remaining } {
        incr otherDoorWins
    }
    if { $winning == $selected } {
        incr firstDoorWins
    }
}

puts "Total number of trials: $trials"
puts "First door wins:        $firstDoorWins - [expr {$firstDoorWins/double($trials)}]"
puts "Other door wins:        $otherDoorWins - [expr {$otherDoorWins/double($trials)}]"