22 Stimmen

Eine Zufallszahl innerhalb eines Bereichs generieren?

Mögliches Duplikat:
Erzeugen von Zufallszahlen in Objective-C

Wie generiere ich eine Zufallszahl, die innerhalb eines Bereichs liegt?

84voto

Jerry Coffin Punkte 452852

Es ist tatsächlich etwas schwieriger, dies richtig zu machen, als die meisten Leute denken:

int rand_lim(int limit) {
/* return a random number between 0 and limit inclusive.
 */

    int divisor = RAND_MAX/(limit+1);
    int retval;

    do { 
        retval = rand() / divisor;
    } while (retval > limit);

    return retval;
}

Versuche, die nur die % (oder, äquivalent, / ), um die Zahlen in einem Bereich zu erhalten, führen fast zwangsläufig zu Verzerrungen (d. h. einige Zahlen werden häufiger erzeugt als andere).

Warum die Verwendung von % führt zu verzerrten Ergebnissen: Wenn der gewünschte Bereich nicht ein Teiler von RAND_MAX ist, ist eine Verzerrung unvermeidlich. Wenn Sie mit kleinen Zahlen beginnen, ist es ziemlich einfach zu sehen, warum. Man nehme 10 Bonbons (von denen man annimmt, dass man sie nicht in kleinere Stücke schneiden, brechen usw. kann) und versuche, sie gleichmäßig auf drei Kinder aufzuteilen. Das ist natürlich nicht möglich - wenn Sie alle Süßigkeiten verteilen, bekommen zwei Kinder höchstens drei Süßigkeiten und eines davon vier.

Es gibt nur einen Weg, damit alle Kinder die gleiche Anzahl an Süßigkeiten bekommen: Du musst dafür sorgen, dass du das letzte Bonbon gar nicht verteilst.

Um dies mit dem obigen Code in Verbindung zu bringen, beginnen wir damit, die Bonbons von 1 bis 10 und die Kinder von 1 bis 3 zu nummerieren. Die anfängliche Division besagt, dass, da es drei Kinder gibt, unser Divisor drei ist. Wir ziehen dann eine zufällige Süßigkeit aus dem Eimer, sehen uns ihre Nummer an, teilen durch drei und geben sie dem Kind. Ist das Ergebnis jedoch größer als 3 (d. h. wir haben die Süßigkeit Nummer 10 ausgewählt), geben wir sie gar nicht aus, sondern werfen sie weg und nehmen eine andere Süßigkeit.

Wenn Sie eine moderne C++-Implementierung verwenden (d. h. eine, die C++11 oder neuer unterstützt), sollten Sie normalerweise die distribution Klassen aus der Standardbibliothek. Der obige Code entspricht am ehesten der std::uniform_int_distribution , aber die Standardbibliothek enthält auch uniform_real_distribution sowie Klassen für eine Reihe von ungleichmäßigen Verteilungen (Bernoulli, Poisson, Normal, vielleicht noch ein paar andere, an die ich mich im Moment nicht erinnere).

7voto

Michał Trybus Punkte 10906
int rand_range(int min_n, int max_n)
{
    return rand() % (max_n - min_n + 1) + min_n;
}

Für Brüche:

double rand_range(double min_n, double max_n)
{
    return (double)rand()/RAND_MAX * (max_n - min_n) + min_n;
}

1voto

John Bode Punkte 112486

Für einen ganzzahligen Wert aus dem Bereich [min,max):

double scale = (double) (max - min) / RAND_MAX;
int val = min + floor(rand() * scale)

-1voto

Philip Regan Punkte 4886

Ich habe dies speziell in Obj-C für ein iPhone-Projekt geschrieben:

- (int) intInRangeMinimum:(int)min andMaximum:(int)max {
    if (min > max) { return -1; }
    int adjustedMax = (max + 1) - min; // arc4random returns within the set {min, (max - 1)}
    int random = arc4random() % adjustedMax;
    int result = random + min;
    return result;
}

Zu verwenden:

int newNumber = [aClass intInRangeMinimum:1 andMaximum:100]; 

Salz nach Geschmack hinzufügen

-2voto

Tom H Punkte 1306
+(NSInteger)randomNumberWithMin:(NSInteger)min WithMax:(NSInteger)max {
    if (min>max) {
        int tempMax=max;
        max=min;
        min=tempMax;
    }
    int randomy=arc4random() % (max-min+1);
    randomy=randomy+min;
    return randomy;
}

Ich verwende diese Methode in einem von mir erstellten Kurs über Zufallszahlen. Funktioniert gut für meine nicht-anspruchsvollen Bedürfnisse, kann aber auch in irgendeiner Weise voreingenommen sein.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X