Bozuk bir rastgele işlevi düzeltin


18

Bir arkadaşının bilgisayarında 1'den 5'e kadar mükemmel rasgele bir sayı üreten bir eklenti kartı vardır. Ne yazık ki, bir şekilde üzerine kola döktüler ve şimdi 1'den 4'e kadar olan tüm sayılar için sadece 2'ler üretiyorlar. 1'ler, 3'ler veya 4'ler üretildi. Bu rastgele kaynağı (buna BrokenRand()benzer bir şey olarak adlandırın ) kullanarak, her biri orijinal kaynakla aynı mükemmel rasgeleliğe sahip% 20 olasılıkla 1 ila 5 arasında sayı üreten bir rasgele sayı üreteci yazın.

En kısa program kazanır. BrokenRandDemografik olarak seçilmiş bir müşteri hizmetleri odak danışmanlığı tarafından yaş ve cinsiyete göre ayrılmış asgari çağrı sayısı için ikramiye puanı - yani ben.

Yanıtlar:


10

JavaScript - 69 karakter

Bu, tarafsız bitler üretmek için von Neumann ekstraktörünü kullanır ; genel algoritma HotBits web sitesinde de açıklanmaktadır . 0 ile 7 arasında bir sayı oluşturmak için üç bit kullanılır. Tüm 5 ve üstü sayılar atılır ve yazdırılmadan önce geri kalanların her birine 1 eklenir. Bunun çok önyargılı olmadığını göstermek için bir simülasyon yaptım .

r()RNG'ye erişmek için kendi işlevinizi sağlamanız gerekir .

 for(;;v<5&&alert(v+1))for(v=i=0;i<3;a-b&&(v*=2,v+=a<b,i++))b=r(a=r())

Bu gerçekten çok iyi! Artış değerini nasıl kısa devre yaptığınızı seviyorum.
snmcdonald

7 bit üretebilir ve BrokenRand çağrılarını azaltmak için 3 rastgele sayı çıkarabilirsiniz, ancak bu muhtemelen birkaç vuruşa mal olur
gnibbler

5

scala 79 karakter:

// preparation: 
val r = util.Random 
def defektRNG = if (r.nextInt (5) == 0) 5 else 2 

(1 to 20).foreach (_ => print (" " + defektRNG))
// first impression:
// 2 2 2 2 2 2 2 5 2 2 5 2 2 2 5 2 2 2 2 2

def rnd : Int = { val k = (1 to 5).map (_ => defektRNG)
  if (k.sum == 13) k.findIndexOf (_ == 5) + 1 else rnd } 

// first impression:
(1 to 20).foreach (_ => print (" " + rnd))             
// 3 3 2 3 5 2 2 5 1 1 3 4 3 2 5 3 3 1 5 4
// control:
(1 to 50000).map (_ => rnd).groupBy (identity) .map (_._2.length) 
// scala.collection.immutable.Iterable[Int] = List(10151, 9997, 9971, 9955, 9926)

Şimdi gerçek golf için defektRNG takma adı brokenRand olarak değiştirildi b.

def r:Int={val k=(1 to 5).map(_=>b)
if(k.sum==13)k.findIndexOf(_==5)+1 else r} 

Nasıl çalışır: Çoğu zaman, b 2'li bir dizi döndürür. Ancak b'ye 5 çağrı yaparsanız, genellikle 4x2 ve 1x5'in bir sonucu ile sonlanırsınız, bu en olası ikinci olaydır ve 5-2-2-2-2, 2-5-2-2 olabilir -2, 2-2-5-2-2, 2-2-2-5-2 ve 2-2-2-2-5.

Bunların ortak yanı, toplamın 4 * 2 + 5 = 13 olmasıdır. İlk beşin indeksi geçerli bir rasgele sayı tanımlamak için kullanılabilir. Birden fazla veya daha az 5, daha büyük veya daha düşük 13 varsa, tekrarlayın.

'Rnd' aka 'r' sayacı, sayıları üretmek için ortalama kaç arama gerektiğini gösterebilir. Etkileyici olmayan 50 000 rasgele sayı için 121 200 çağrı vardır. :)


3

> <> (Balık) - 55 bayt

Onun scala cevabında bilinmeyen @ kullanıcı ile aynı algoritmayı kullanacak şekilde güncellendi

? <V d = + i ve + i ve + i ve + i & i
 0
 > 1 + 5 $ (vnao;
 ^ <

Kırık jeneratörün stdin'e bağlanmasını bekler; İşte kullandığım python betiği . Kod, mevcut Fish spesifikasyonuyla eşleşiyor, ancak eski yorumlayıcının değiştirilmiş bir versiyonunu kullandım .

bash:$ for i in $(seq 1000); do ./bad_rand.py | ./myfish.py rand.fish; done >res.txt
bash:$ for i in $(seq 5); do echo -n "$i : "; grep -c $i res.txt; done
1 : 193
2 : 204
3 : 198
4 : 206
5 : 199

Daha büyük bir örnek yapardım ama yavaş.


2

GolfScript, 23 bayt

Geç cevap, ama bu sadece ön sayfada ortaya çıktığı için ...

0{;[{r}5*].5?)\5-,4-}do

Bilinmeyen kullanıcı Scala çözümü ile aynı algoritmayı kullanır . Önyargılı rasgele sayı üretecinin bir GolfScript alt yordamı olarak verildiğini varsayar r; kendiniz için uygun bir önyargılı RNG tanımlayabilirsiniz:

{5rand!3*2+}:r;

İşte önyargı eksikliğini gösteren hızlı bir test. Ne yazık ki, çevrimiçi GolfScript sunucusu biraz yavaş, bu yüzden gösteriyi zamanında tamamlamak için sadece 100 örneğe kesmek zorunda kaldım. İle yerel testi çalıştıran varsa GolfScript tercüman , artırmayı deneyin 100*için 1000*hatta 10000*.

(GolfScript sunucusu da bazen rastgele donar ve yine de zaman aşımına uğrar. Bu sizin için olursa, tekrar denemek genellikle onu çözer. Diğer kodla da olur ve sadece kendi bilgisayarımda değil, sunucuda olur, bu yüzden kendime güveniyorum kodumda değil sunucuda bir sorun olduğunu.)


-1

javascript, okunabilirliği azaltmadan 160 karakter, optimizasyon

function giveRandom(){
    var result = Math.floor(5 * Math.random()) + 1;
    while(BrockenRand() != 5){
        result = Math.floor(5 * Math.random()) + 1;
    }
    return result;
}

@ snmcdonald -bazı yazım hatası değil, sadece onaylayan mükemmel bir rastgele jeneratör js rastgele geliştirmek için bir yol (tamamen rastgele!)% 20 sonuç
www0z0k

Ne BrockenBand()olduğunu açıklamak ister misiniz?
Mateen Ulhaq

6
Sanırım noktayı kaçırdınız
cthom06

@muntoo - AnlamıBrockenRand
www0z0k

Bu şekilde birkaç bayt kaydedin:function giveRandom(){return Math.ceil(Math.random()*5)}
user300375
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.