Skip to content

Instantly share code, notes, and snippets.

@UlisseMini
Last active December 5, 2021 03:06
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save UlisseMini/5ec04e42b54e5d2919e6f9ba54bdebec to your computer and use it in GitHub Desktop.
Save UlisseMini/5ec04e42b54e5d2919e6f9ba54bdebec to your computer and use it in GitHub Desktop.
Bunny problem: https://uli.rocks/p/bunny
N = 100
def guess(P, j):
# after setting P[j] = 0 we have removed P[j] probability mass from
# the distribution, so the new sum is 1-P[j]. Dividing everything by
# 1-P[j] fixes this. (a minor detail, instead of 1 we use sum(P) for
# numerical stability since sum(P) isn't exactly 1)
s = sum(P) - P[j]
return [
0 if i == j else P[i] / s
for i in range(N)
]
def jumps(P):
Pn = P.copy()
Pn[0] = P[1]*0.5
Pn[N-1] = P[N-2]*0.5
for j in range(1, N-1):
Pn[j] = 0.5*P[j-1] + 0.5*P[j+1]
return Pn
import random
def argmax(l):
return max(range(len(l)), key=lambda i: l[i])
def play():
P = [1/N] * N
hole = random.randint(0, N-1)
t = 0
while True:
t += 1
j = argmax(P)
# uncomment for random guessing strategy
# j = random.randint(0, N-1)
if j == hole:
print(f'Found the bunny in hole {j} after {t} tries!')
break
else:
#print(f'[{t}] Guessed {j} with P[{j}] = {P[j]:.4f} (true is {hole})')
# wrong hole, update our beliefs
P = guess(P, j)
P = jumps(P)
# the bunny moves!
if hole == 0: hole += 1
elif hole == N-1: hole -= 1
else: hole += random.choice([-1, 1])
return t
r = [play() for _ in range(10000)]
import statistics as stats
mean, median, stdev = stats.mean(r), stats.median(r), stats.stdev(r)
print(f'mean: {mean} median: {median} stddev {stdev}')
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment