Forum Programmation.c Question sur les fonctions RAND et SRAND

Posté par  .
Étiquettes : aucune
0
27
déc.
2006
Bonjour,

J'ai vu que srand permettait la génération d'une suite aléatoire
et rand() une valeur aléatoire, (pseudo-aléatoire ne chippotons pas sur les termes :) , hors je voulais utiliser ces fonctions pour créer un fichier bidon qui servira a tester un mini-programme.

Hors je vois en lisant les résultats de ce mini programme que les chiffres générés sont tjrs les mêmes durant l'uptime de la machine.

comment résoudre ça ?

est ce que faire un ajout comme celui là résoudra le problème ?

[code]
....
#include <time.h>

....
....
srand(time(NULL));
....
Val_noeud=rand()%100+20;
.....
[/code]

à la place de l'actuell
[code]
....
srand();
....
[/code]

celà résoudra t il le problème ?

[b]PS[/b]: Je compilerai sur des gcc versions < à 3.3 (la machine de test actuellement compile en gcc 3.3 ou 4.0.2 au choix)
  • # Ce commentaire n'a pas de titre

    Posté par  . Évalué à 1.

    srand()/rand() ne permettent de générer que des suites pseudo-alétoires (et c'est pas du chippotage, toute la suite dépend de la graine et l'entropie est donc complètement à chier).

    Ta solution est tout aussi mauvaise pour générer de l'aléatoire, mais effectivement remplacer srand() par srand(time(NULL)) permet de générer une suite différente à chaque éxécution.
  • # Pseudo-aléa et initialisation

    Posté par  . Évalué à 5.

    Comme tu l'as toi-même précisé, rand renvoie une valeur pseudo-aléatoire. srand initialise la graine de génération du pseudo-aléa retourné par rand. La norme C spécifie que, dans une implémentation donnée, pour une valeur de la graine, la suite de valeurs retournée par des appels successifs à rand doit être la même (mais cette suite peut être différente entre différentes implémentations, heureusement d'ailleurs).

    De plus, l'appel à rand sans avoir appelé srand revient à renvoyer le même pseudo-aléa qu'avec la graine 1. Il est donc normal que, sans srand, ton programme se comporte toujours de la même manière à chaque fois que tu l'appelles.

    Dixit le n1124 :

    7.20.2 Pseudo-random sequence generation functions
    7.20.2.1 The rand function
    Synopsis

    #include <stdlib.h>
    int rand(void);

    Description

    The rand function computes a sequence of pseudo-random integers in the range 0 to RAND_MAX.
    The implementation shall behave as if no library function calls the rand function.

    Returns

    The rand function returns a pseudo-random integer.

    Environmental limits

    The value of the RAND_MAX macro shall be at least 32767.

    7.20.2.2 The srand function

    Synopsis

    #include <stdlib.h>

    void srand(unsigned int seed);

    Description

    The srand function uses the argument as a seed for a new sequence of pseudo-random numbers to be returned by subsequent calls to rand. If srand is then called with the same seed value, the sequence of pseudo-random numbers shall be repeated. If rand is called before any calls to srand have been made, the same sequence shall be generated as when srand is first called with a seed value of 1.

    The implementation shall behave as if no library function calls the srand function.

    Returns

    The srand function returns no value.

    EXAMPLE The following functions define a portable implementation of rand and srand.
    static unsigned long int next = 1;
    int rand(void) // RAND_MAX assumed to be 32767
    {
        next = next * 1103515245 + 12345;
        return (unsigned int)(next/65536) % 32768;
    }

    void srand(unsigned int seed)
    {
        next = seed;
    }


    Une manière classique de choisir une graine pour srand, que tu as reprise dans ton code, est de récupérer la date courante par un appel time(NULL) (*). Ainsi, la graine sera différente à chaque exécution de ton programme (pourvu que ton programme ne soit pas lié à une libc "customisée" ;-) ), et donc la suite de pseudo-aléa sera différente.

    En passant, ces fonctions font partie de la bibliothèque C standard, donc dans ton contexte très probablement de la glibc, pas de gcc (qui n'inclut pas de bibliothèque C).

    (*) time renvoie une valeur de type time_t, alors que srand attend un unsigned int. Ce n'est pas grave, la conversion implicite se fera si besoin. Les considérations sur la qualité de la graine qui en découlent sont un peu trop complexes... (de toute façon, si on vient à se poser cette question, il est probable qu'on cherchera à utiliser un autre générateur de pseudo-aléa que celui fourni par défaut)
  • # une lecture de /dev/urandom ça ne le ferait pas?

    Posté par  . Évalué à 0.

    La question est dans le titre ....
  • # MERCI

    Posté par  . Évalué à 2.

    Je vous remercie en fait ça marche tres bien avec
    srand(time(NULL));

    par contre utiliser /dev/random ou urandom est une mauvaises soluion parceque d'un systèeme unix à un autre ou à un linux / BSD c'est pas forcément le même nom.

    la solution interne au source C est donc la seule qui puisse me convenir.

    meci encore

    joyeux reveillon et à bientot.

Suivre le flux des commentaires

Note : les commentaires appartiennent à celles et ceux qui les ont postés. Nous n’en sommes pas responsables.