/* Unbiased coin in Picat. https://brainstellar.com/puzzles/probability/19 """ We have a weighted coin that shows a Head with probability p and tails with 1-p (0.5 < p < 1). How to define two equally likely events using this coin? Each event is a function of the outcomes of one or more coin tosses. For example, we can toss 2 times and define Event1 as [HH, TT] and Event2 as [TH, HT]. Hint: Since p is unknown, the probability of HH and TT are unreliable. Answer: Toss 2 times, event1 is HT, event2 is TH, and repeat the process otherwise. """ Cf - ppl_fair_coin_from_a_biased_coin.pi - my Gamble model gamble_unbiased_coin.rkt This program was created by Hakan Kjellerstrand, hakank@gmail.com See also my Picat page: http://www.hakank.org/picat/ */ import ppl_distributions, ppl_utils. import util. main => go. /* var : a Probabilities: t: 0.5185000000000000 h: 0.4815000000000000 mean = [t = 0.5185,h = 0.4815] var : p Probabilities (truncated): 0.999960983686323: 0.0001000000000000 0.999929550392266: 0.0001000000000000 0.999893648393781: 0.0001000000000000 0.999886199716169: 0.0001000000000000 ......... 0.500246085503899: 0.0001000000000000 0.500095186221973: 0.0001000000000000 0.500079638665432: 0.0001000000000000 0.500053389352538: 0.0001000000000000 mean = 0.749964 var : two coins Probabilities: hh: 0.5835000000000000 th: 0.1670000000000000 ht: 0.1649000000000000 tt: 0.0846000000000000 mean = [hh = 0.5835,th = 0.167,ht = 0.1649,tt = 0.0846] */ go ?=> reset_store, run_model(10_000,$model,[show_probs_trunc,mean]), nl, % show_store_lengths,nl, % fail, nl. go => true. coin(P) = condt(flip(P),h,t). f(P) = Res => C1 = coin(P), C2 = coin(P), if C1 != C2 then Res = C1 else Res = f(P) end. model() => % P should be > 0.5 P0 = beta_dist(1,1), % P0 = 0.8, P = cond(P0 < 0.5,1-P0,P0), TwoCoins = [coin(P) : _ in 1..2], % The strategy in the Answer above A = f(P), add("p",P), add("two coins",TwoCoins), add("a",A).