Ich habe das schon mal gemacht, aber jetzt mit ihm wieder ich bin zu kämpfen, und ich glaube, ich bin nicht die Mathematik zu verstehen, um das Problem zu Grunde liegen.
Ich möchte auf in einem kleinen Bereich auf beiden Seiten 1
eine Zufallszahl einzustellen. Beispiele wären .98
, 1.02
, .94
, 1.1
usw. Alle Beispiele finde ich beschreiben zwischen 0
und 100
eine Zufallszahl bekommen, aber wie kann ich das innerhalb bekommen verwenden die Strecke, die ich will?
Die Programmiersprache ist nicht wirklich wichtig hier, obwohl ich Pure Data verwenden. Könnte jemand bitte die Mathematik erklären?
Wenn Sie eine (pseudo) gleichmäßige Verteilung (gleichmäßig verteilt) zwischen 0.9 und 1.1 wünschen, dann funktioniert das Folgende:
%Vor%Passen Sie den Bereich entsprechend an.
Wenn Sie eine Normalverteilung (Glockenkurve) wünschen, benötigen Sie speziellen Code, der spezifisch für Sprache / Bibliothek ist. Sie können eine enge Annäherung mit diesem Code erhalten:
%Vor% Um eine Zufallszahl innerhalb eines Bereichs zu erhalten, erhalten Sie keine Zahl zwischen 0
und 100
. Sie erhalten eine Zahl zwischen 0
und 1
. Dies ist jedoch inkonsequent, da Sie einfach die 0
- 1
-Nummer erhalten, indem Sie Ihre # durch 100
teilen - also werde ich den Punkt nicht belasten.
Wenn Sie über den Pseudocode nachdenken, müssen Sie sich die Anzahl zwischen 0
und 1
vorstellen, die Sie als Prozentsatz erhalten. Mit anderen Worten, wenn ich einen willkürlichen Bereich zwischen a
und b
habe, ist der Prozentsatz des Weges zwischen den beiden Endpunkten der Punkt, den ich zufällig ausgewählt habe. (Ein zufälliges Ergebnis von 0.52
bedeutet also 52%
der Entfernung zwischen a
und b
)
Denken Sie in diesem Zusammenhang an das Problem:
Stellen Sie den Start- und Endpunkt Ihres Bereichs ein.
var min = 0.9;
var max = 1.1;
Erhalte eine Zufallszahl zwischen 0
und 1
var random = Math.random();
Nehmen Sie die Differenz zwischen Ihrem Start- und Endbereich ( b
- a
)
var range = max - min;
Multiplizieren Sie Ihre Zufallszahl mit der Differenz
var adjustment = range * random;
Fügen Sie Ihren Mindestwert hinzu.
var result = min + adjustment;
Und damit Sie die Werte jedes Schrittes in der Reihenfolge verstehen können:
%Vor% Beachten Sie, dass das Ergebnis garantiert in Ihrer Reichweite liegt. Der minimale Zufallswert ist 0
und der maximale Zufallswert ist 1
. In diesen beiden Fällen geschieht Folgendes:
Wenn rand () eine Zufallszahl zwischen 0 und 100 zurückgibt, müssen Sie nur:
%Vor%, um eine Zufallszahl zwischen 0 und 2 zu erhalten.
Wenn Sie andererseits den Bereich von 0,9 bis 1,1 wünschen, verwenden Sie Folgendes:
%Vor%Sie können beliebige Distributionen, die Sie möchten, im Bereich [0,1] einheitlich gestalten, indem Sie die Variable ändern. Insbesondere, wenn Sie eine zufällige Verteilung mit der kumulativen Verteilungsfunktion F wünschen, ersetzen Sie einfach die gleichförmige Zufallszahl von [0,1] durch die Umkehrfunktion für die gewünschte CDF.
Ein spezieller (und vielleicht populärster) Fall ist die Normalverteilung N (0,1). Hier können Sie Box-Muller-Transformation verwenden. Wenn Sie es mit stdev skalieren und einen Mittelwert hinzufügen, erhalten Sie eine normale Verteilung mit den gewünschten Parametern.
Sie können uniforme Zufallszahlen summieren und eine Annäherung an die Normalverteilung erhalten, dieser Fall wird von Nick Fortescue oben betrachtet.
Wenn Ihre Source-Randoms ganze Zahlen sind, sollten Sie zuerst eine zufällige Domain mit einer bekannten Distribution erstellen. Zum Beispiel, die gleichmäßige Verteilung in [0,1) können Sie solchen Weg konstruieren. Sie erhalten die erste ganze Zahl im Bereich von 0 bis 99, multiplizieren Sie sie mit 0,01, erhalten Sie die zweite ganze Zahl, multiplizieren Sie sie mit 0,0001 und addieren Sie zum ersten und so weiter. Auf diese Weise erhalten Sie eine Zahl 0.XXYYZZ ... Doppelte Genauigkeit ist etwa 16 Dezimalstellen, so dass Sie 8 Integer-Zufallszahlen benötigen, um eine doppelte einheitliche Zahl zu konstruieren.
Box-Müller zur Rettung.
%Vor%Verwenden Sie mit Werten von Mittelwert 1 und Varianz z. 0,01
%Vor%Funktion ergibt ca. Normalverteilung um Mittelwert bei gegebener Varianz.
Wie nahe? Sie könnten eine Gaußsche (alias normal) Verteilung mit einem Mittelwert von 1 und einer kleinen Standardabweichung verwenden.
Ein Gaussian ist geeignet, wenn Zahlen nahe 1 häufiger vorkommen als Zahlen, die etwas weiter von 1 entfernt sind.
Einige Sprachen ( wie Java ) wird Unterstützung für Gaussianer in der Standardbibliothek haben.
Teile durch 100 und addiere 1. (Ich nehme an, du suchst einen Bereich von 0 bis 2?)
Rand () gibt Ihnen bereits eine Zufallszahl zwischen 0 und 100. Die maximal mögliche Zufallszahl, die Sie damit erhalten können, ist 100. Vorausgesetzt, Sie möchten bis zu drei Dezimalzahlen 0.950-1.050
ist der Bereich, den Sie betrachten würden .
Die Verteilung kann dann durch
erreicht werden %Vor%Suchst du nach dem Zufalls-Nr. von Bereich 1 bis 2, wie 1,1,1,5,1,632, usw. Wenn ja, dann ist hier ein einfacher Python-Code:
%Vor%Für Zahlen von 0.9 bis 1.1
seed = 1
Bereich = 0,1
wenn Ihr Zufall von 0..100
istf_rand = zufällig / 100
die generierte Nummer
gen_number = (Seed + f_rand * Bereich * 2) -range
Sie werden bekommen 1,04; 1,08; 1,01; 0,96; ...
mit Seed 3, Bereich 2 = & gt; 1,95; 4,08; 2,70; 3,06; ...
Ich habe das nicht verstanden (sorry):
Ich versuche, eine Zufallszahl auf beiden Seiten von 1: .98, 1.02, .94, 1.1 usw. zu setzen.
Also, ich werde stattdessen eine allgemeine Lösung für das Problem bereitstellen.
Wenn Sie einen Zufallszahlengenerator in einem Give-Bereich [0, 1) * mit einheitlicher Verteilung haben, können Sie ihn mit der folgenden Methode in eine beliebige Distribution konvertieren:
1 - Beschreibe die Verteilung als eine Funktion, die im Ausgabebereich und mit einer Gesamtfläche von 1 definiert ist. Also ist diese Funktion f (x) = die Wahrscheinlichkeit, den Wert x zu erhalten.
2 - Integriere ** die Funktion.
3 - Gleichsetzen Sie es mit dem "randomic" * .
4 - Löse die Gleichung für x. So ti gibt dir den Wert von x in Funktion des Randomic.
*: Die Verallgemeinerung für jede Eingabeverteilung ist unten.
**: Der konstante Ausdruck der integrierten Funktion ist 0 (dh Sie verwerfen ihn einfach).
**: Das ist eine Variable, die das Ergebnis der Generierung einer Zufallszahl mit einheitlicher Verteilung im Bereich [0, 1] darstellt. [Ich bin mir nicht sicher, ob das der richtige Name auf Englisch ist]
Beispiel :
Nehmen wir an, Sie möchten einen Wert mit der Distribution f(x)=x^2 from 0 to 100
. Nun, diese Funktion ist nicht normalisiert, weil die Gesamtfläche unterhalb der Funktion im Bereich 1000000/3 nicht 1 ist. Sie normalisieren also die Kurve in der vertikalen Achse (unter Beibehaltung der relativen Proportionen), die durch die Gesamtfläche dividiert: f(x)=3*x^2 / 1000000 from 0 to 100
.
Nun haben wir eine Funktion mit einer Gesamtfläche von 1. Der nächste Schritt besteht darin, sie zu integrieren (Sie haben dies vielleicht bereits getan, um die Fläche zu erhalten) und sie mit der Randomik zu verknüpfen.
Die integrierte Funktion ist: F(x)=x^3/1000000+c
. Und setzen Sie es mit dem Randomic: r=x^3/1000000
(denken Sie daran, dass wir den konstanten Ausdruck verwerfen).
Nun müssen wir die Gleichung für x lösen, den resultierenden Ausdruck: x=100*r^(1/3)
. Jetzt können Sie diese Formel verwenden, um Zahlen mit der gewünschten Verteilung zu generieren.
Generalisierung
Wenn Sie einen Zufallszahlengenerator mit einer benutzerdefinierten Verteilung haben und eine andere willkürliche Verteilung wünschen, benötigen Sie zuerst die Quellenverteilungsfunktion und verwenden Sie sie dann, um den Ziel-Zufallszahlengenerator auszudrücken. Um die Verteilungsfunktion zu erhalten, führe die Schritte bis zu 3. Für das Ziel führe alle Schritte aus und ersetze dann den Randomic durch den Ausdruck, den du von der Quellverteilung erhalten hast.
Dies wird besser mit einem Beispiel verstanden ...
Beispiel :
Sie haben einen Zufallszahlengenerator mit einer gleichmäßigen Verteilung im Bereich [0, 100] und Sie wollen .. die gleiche Verteilung f(x)=3*x^2 / 1000000 from 0 to 100
für die Einfachheit [Da für diesen einen haben wir bereits alle Schritte gemacht% x=100*r^(1/3)
] .
Da die Quellenverteilung einheitlich ist, ist die Funktion konstant: f(z)=1
. Aber wir müssen für den Bereich normalisieren und uns damit verlassen: f(z)=1/100
.
Jetzt integrieren wir es: F(z)=z/100
. Und setze es mit randomic: r=z/100
, aber dieses Mal lösen wir es nicht für x, sondern verwenden es, um r im Ziel zu ersetzen:
Und jetzt können Sie x=z^(1/3)
verwenden, um Zufallszahlen mit der Verteilung f(x)=3*x^2 / 1000000 from 0 to 100
zu berechnen, die mit einer Zufallszahl in der Distribution f(z)=1/100 from 0 to 100
[uniform] beginnt.
Hinweis: Wenn Sie eine Normalverteilung haben, verwenden Sie stattdessen die Glockenfunktion. Die gleiche Methode funktioniert für jede andere Distribution. Achten Sie auf mögliche Asymptoten, die einige Distributionen erzeugen, müssen Sie möglicherweise verschiedene Wege versuchen, um die Gleichungen zu lösen.
Bei diskreten Verteilungen
Manchmal müssen Sie eine diskrete Verteilung ausdrücken, z. B. möchten Sie 0 mit 95% Chance und 1 mit 5% Chance erhalten. Wie machst du das?
Nun, Sie teilen es in rechteckige Verteilungen so auf, dass die Bereiche zu [0, 1] zusammenkommen und verwenden Sie den Randomic um auszuwerten:
%Vor%Oder Sie können den komplexen Pfad verwenden, der eine Verteilungsfunktion wie folgt beschreibt (wobei jede Option genau einen Bereich der Länge 1 hat):
%Vor%Da jeder Bereich eine Länge von 1 hat und die zugewiesenen Werte 1 ergeben, wissen wir, dass die Gesamtfläche 1 ist. Nun wäre der nächste Schritt, sie zu integrieren:
%Vor%Gleichsetzen Sie es mit dem Randomic:
%Vor%Und löse die Gleichung ...
Ok, um diese Art von Gleichung zu lösen, beginnen Sie mit der Berechnung der Ausgabebereiche durch Anwendung der Funktion:
%Vor%Nun, das sind die Bereiche für die Lösung:
%Vor%Löse nun die inneren Funktionen:
%Vor%Da die Ausgabe jedoch diskret ist, erhalten wir nach der Ausführung eines ganzzahligen Teils das gleiche Ergebnis:
%Vor%Hinweis: Verwenden Sie "zufällig", um pseudozufällig zu sein.
Bearbeiten : Es wurde auf wikipedia gefunden (ich wusste, dass ich es nicht erfunden habe) .