random zahl in schranken berechnen.

Gast #1155668
Lesenswert?

Du meinst wahrscheinlich dieses:
1
v' =(int)((double)v*80/RAND_MAX)*5 + 10;

Erst einmal ist das nicht richtig oder zumindest nicht das, was der
Frager im anderen Forum wahrscheinlich wollte. Er wollte eine
Zufallszahl aus {10,15,20,25,...,400,405,410}. Da er keine
Wahrscheinlichkeitsverteilung angegeben hat, nehme ich an, dass er eine
Gleichverteilung wollte. Der Ausdruck liefert aber nur dann 410, wenn
v=RAND_MAX ist, wofür die Wahrscheinlichkeit 1/(RAND_MAX+1) und damit
viel kleiner als die gewünschten 1/81 sein. Richtig wäre
1
v' =(int)((double)v*81/(RAND_MAX+1))*5 + 10;
2
                    ^^          ^^

Ansonsten entspricht das Vorgehen dem von Rufus vorgschlagenen. Da C nur
einen Integer-Zufallszahlengenerator hat, muss man den Zufallswert durch
RAND_MAX dividieren, um den Wertebereich [0.0,1.0] zu erhalten. Diesen
kann man durch eine anschließende Multiplikation und Addition nach
Belieben Skalieren und Verschieben.

Wenn du also FP-Zahlen im Intervall [5.0,100.0] (einschließlich der
Grenzen) möchtest, geht das so:
1
  double z;
2
  z = 95.0 * (double)rand() / RAND_MAX + 5.0;

Möchtest du Integerzahlen (also 5,6,7,...,94,95), machst du folgendes:
1
  int z;
2
  z = (int)(96.0 * (double)rand() / (RAND_MAX+1)) + 5;

Stören dich dabei die FP-Operationen, geht es auch so:
1
  int z;
2
  z = rand() % 96 + 5;

Diese Lösung ist aber nicht ganz exakt: Da RAND_MAX+1 nicht durch 96
teilbar ist. sind die Restklassen modulo 96 nicht alle gleich groß,
weswegen auch die Wahrscheinlichkeiten für die 96 möglichen Ergebnisse
nicht alle gleich groß sind. Das kann folgendermaßen korrigiert werden:
1
  int r, z;
2
  do
3
    r = rand();
4
  while(r >= (RAND_MAX+1) / 96 * 96);
5
  z = r % 96 + 5;

Durch die Schleife wird der Wertebereich der rand-Funktion von oben her
auf ein Vielfaches von 96 abgeschnitten, so dass die Ergebnisse für z
tatsächlich gleichverteilt sind. Nachteil: Durch die Schleife ist die
Rechenzeit nicht nach oben beschränkt, so dass das Verfahren nicht in
hart echtzeitkritischen Systemen eingesetzt werden kann. Für "normale"
Anwendungen ist es aber in Ordnung, da die Schleife nur in sehr seltenen
Fällen mehr als einmal durchlaufen wird und somit die mittlere
Rechnzeit (insbesondere auf Rechnern ohne FPU) geringer als bei der
FP-Lösung ist.

So, jetzt kannst du dir einer der vier Alternativen aussuchen oder dir
eine weitere ausdenken.
#1155723
Lesenswert?

yalu wrote:

>
1
>   int z;
2
>   z = rand() % 96 + 5;
3
>
>
> Diese Lösung ist aber nicht ganz exakt: Da RAND_MAX+1 nicht durch 96
> teilbar ist. sind die Restklassen modulo 96 nicht alle gleich groß,
> weswegen auch die Wahrscheinlichkeiten für die 96 möglichen Ergebnisse
> nicht alle gleich groß sind.

Nur der Vollständigkeit halber, weil das sonst unter Umständen 
misverstanden werden kann. Die ursprünglich vorgeschlagene Lösung, mit 
der Division durch RAND_MAX bzw. RAND_MAX+1 hat genau dasselbe Problem.
In der Mathematik nennt man das Problem das 'Schubladenproblem': Es ist 
unmöglich n Gegenstände in m Schubladen zu legen sodass in jeder 
Schublade gelich viele Gegenstände liegen, wenn n kein Vielfaches von m 
ist.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren