lehrkraefte:blc:informatik:ffprg1-2020:zufallszahlen

Zufallszahlen

Für Spiele und Simulationen sind Zufallszahlen äusserst nützlich. Auch für kryptographische Anwendungen werden Zufallszahlen gebraucht. Dafür sind die Zufallszahlen von Python aber nicht geeignet. Und sowieso: Programmieren Sie nie selbst Krypto (es sei denn, Sie machen seit 10 Jahren nichts anderes, als Kryptographie und Computerinnereien zu studieren).

zufall.py
import random
 
print("Floats, uniform von 0.0 bis ohne 1.0")
for i in range(10):
    print(random.random())
 
# Ich bevorzuge random.randrange weil es gleich wie range funktioniert
print("Ints, uniform von 0 bis und mit 3")
for i in range(10):
    print(random.randrange(4))
 
# Ich rate von random.randint ab und empfehle random.randrange 
print("Ints, uniform von 1 bis und mit 6")
for i in range(10):
    print(random.randint(1,6))

random.randrange(a,b,s) wählt ein zufälliges Element aus range(a,b,s) aus.

Detaillierte Übersicht: https://machinelearningmastery.com/how-to-generate-random-numbers-in-python/

  • Generieren Sie 10 Zufallszahlen (floats) zwischen 10.0 (inklusive) und 20.0 (exklusive).
  • Welchen Wert erhält man im Durchschnitt, wenn man mit zwei Würfeln auf einmal würfelt und sich jeweils den grösseren der beiden Werte notiert?
    • Challenge: Können Sie den Wert exakt berechnen? Wie sieht es mit $3$ und mehr Würfeln aus? Wie mit $n$?
  • Generieren Sie $n=10000$ mal einen zufälligen Punkt im Einheitsquadrat $[0,1] \times [0,1]$. Wie viele davon liegen im Einheitskreis (d.h. im Kreis mit Radius 1 um den Ursprung)? Wie viele müssten es sein? Berechnen Sie daraus eine Schätzung für $\pi$.

Lösungsvorschläge

Lösungsvorschläge

float10bis20.py
import random
 
print("Floats, uniform von 10.0 bis ohne 20.0")
for i in range(10):
    print(random.random()*10+10)

Simulation Maximum zweier Würfel:

maxwurf2.py
import random
n=100000
s = 0
for i in range(n):
    w1 = random.randint(1,6)
    w2 = random.randint(1,6)
    if w1>w2:
        s+=w1
    else:
        s+=w2
print("Durchschnitt (mit n=%d Versuchen): %f" % (n,s/n))

Oder noch eine kompaktere Variante mit Arrays:

maxwurfarray.py
import random
n=100000
numWurfel=2
s = 0
for i in range(n):
    s += max([random.randint(1,6) for j in range(numWurfel)])
print("Durchschnitt (mit n=%d Versuchen und %d Würfeln): %f" % (n,numWurfel,s/n))

Und exakt (durch Aufzählen aller Möglichkeiten)

maxwurf2exakt.py
n = 0
s = 0
for w1 in range(1,7):
    for w2 in range(1,7):
        s+=max(w1,w2)
        n+=1
print("Durchschnitt exakt %d/%d ~ %f" % (s,n,s/n))

Allgemein exakt. Um die Mathematik zu verstehen, denken Sie sich für n=2 Würfel ein 6×6 Raster und markieren Sie jene Felder, die zu einem gegebenen Maximum $m$ führen. Deren Anzahl kann als Differenz zweier Quadrate (bzw. Hyperwürfel für $n>2$) berechnet werden.

maxwurfexakt.py
numWurf = 2
n = 6**numWurf
s = 0
for w in range(1,7):
    s+=w*(w**numWurf-(w-1)**numWurf)
 
print("Durchschnitt exakt %d/%d ~ %f" % (s,n,s/n))
kreisimquadrat.py
import random
n = 1000000
s = 0
for i in range(n):
    r = random.random()**2+random.random()**2
    if (r<=1):
        s+=1
 
print("Durchschnitt %f, Schätzung für pi ~ %f" % (s/n, s/n*4))
  • lehrkraefte/blc/informatik/ffprg1-2020/zufallszahlen.txt
  • Last modified: 2022/05/12 13:34
  • by Ivo Blöchliger