HOWTO · C++

Wie man eine Zufallszahl zwischen 0 und 1 in C++ generiert

Dieser Artikel zeigt, wie man eine Zufallszahl zwischen 0 und 1 Intervall C++

Auf dieser Seite

Um einen pseudozufälligen Gleitkommawert von 0 bis knapp unter 1 zu erzeugen, kombinieren Sie eine C++11-Zufallsengine mit std::uniform_real_distribution<double>. Das Beispiel verwendet einen festen Seed. Damit lässt sich dieselbe Sequenz mit derselben Engine und demselben Seed auf einer bestimmten Implementierung reproduzieren. Verwenden Sie <random> für neuen C++-Code; behalten Sie std::rand der Wartung älteren Codes vor.

Mit C++11 <random> eine Gleitkommazahl erzeugen

Binden Sie <random> ein, erstellen Sie eine Engine und übergeben Sie sie jedes Mal einer Verteilung, wenn Sie einen Wert benötigen. Eine Engine erzeugt eine Folge pseudozufälliger Bits; die Verteilung bildet diese Bits auf Werte des gewünschten Typs und Wertebereichs ab. Dieses vollständige Beispiel gibt fünf Werte aus. Dank des festen Seeds sind erneute Läufe mit derselben Standardbibliotheksimplementierung reproduzierbar.

#include <iostream>
#include <random>

int main() {
    std::mt19937 engine(2026);
    std::uniform_real_distribution<double> distribution(0.0, 1.0);

    for (int i = 0; i < 5; ++i) {
        std::cout << distribution(engine) << '\n';
    }
}

Die ausgegebenen Ziffern hängen von der Standardbibliotheksimplementierung ab. Auf derselben Implementierung beginnt die Folge bei gleicher Engine und gleichem Seed stets gleich. Für eine andere Folge können Sie einen anderen Seed verwenden oder die Engine einmal mit std::random_device initialisieren. Dieses Gerät liefert jedoch nicht auf jedem System nichtdeterministische Entropie.

Ausgabebereich verstehen und eine Engine auswählen

Für std::uniform_real_distribution<double>(0.0, 1.0) ist das festgelegte Intervall halboffen: Der Wert 0 kann zurückgegeben werden, 1 ist ausgeschlossen. Das Template-Argument legt den Gleitkomma-Rückgabetyp fest (float, double oder long double). Eine Verteilung benötigt eine Engine als Argument; sie ist kein eigenständiger Generator.

Die Engine bestimmt die pseudozufällige Folge, und der Seed legt fest, an welcher Stelle dieser Folge begonnen wird. std::mt19937 ist eine weit verbreitete Standard-Engine mit festgelegtem Algorithmus. std::default_random_engine ist praktisch, wenn die konkrete Engine keine Rolle spielt. Da ihre Auswahl von der Implementierung abhängt, eignet sie sich weniger, wenn Sie über verschiedene Standardbibliotheken hinweg dieselbe Folge benötigen. Setzen Sie den Seed einmal und verwenden Sie die Engine wieder; ein erneutes Setzen vor jeder Ziehung kann Werte wiederholen und die Folge beeinträchtigen. Diese Funktionen eignen sich für Simulationen, Spiele und gewöhnliche Zufallsabläufe, aber nicht für kryptografische Geheimnisse.

std::rand nur für älteren Code verwenden

Älterer Code verwendet möglicherweise std::rand, deklariert in <cstdlib>. Die Funktion gibt eine ganze Zahl von 0 bis einschließlich RAND_MAX zurück. Wandeln Sie den Wert vor der Division in einen Gleitkommatyp um, damit keine Ganzzahldivision erfolgt. Der Inline-Ausdruck static_cast<double>(std::rand()) / (static_cast<double>(RAND_MAX) + 1.0) skaliert die ganze Zahl beispielsweise auf den gewünschten Wertebereich.

Durch diese Skalierung bleibt das Ergebnis unter 1, auch wenn std::rand den Wert RAND_MAX zurückgibt. Wenn die Werte zwischen Läufen variieren sollen, rufen Sie vor der Erzeugung einmal std::srand auf, häufig mit einem zeitabhängigen Seed. Bei wiederholten Läufen kann trotzdem derselbe Seed verwendet werden, und das Setzen eines Seeds verbessert nicht die Qualität des Generators. RAND_MAX hängt von der Implementierung ab, und std::rand bietet weniger Kontrolle über Engine und Folge als <random>. Bevorzugen Sie für neuen Code die C++11-Engine und -Verteilung; verwenden Sie die ältere Funktion nur, wenn eine vorhandene Schnittstelle sie erfordert.