Exercice : Générer un code de 4 nombres aléatoires, différentes
WhiteTiger851
Messages postés
26
Date d'inscription
Statut
Membre
Dernière intervention
-
Dalfab Messages postés 706 Date d'inscription Statut Membre Dernière intervention -
Dalfab Messages postés 706 Date d'inscription Statut Membre Dernière intervention -
Bonjour,
Je sais comment générer un code 4 nombres aléatoires :
Mais, comment avoir un code avec des nombres différents ?
J'ai essayé de faire ça :
Mais, ça ne fonctionne pas. Pouvez-vous m'aidez ?
Merci
Je sais comment générer un code 4 nombres aléatoires :
<ital>#include <stdio.h> #include <time.h> #define TAILLE 4 #define NB_VALEURS 10 void CodeAlea(int tab[],int taille){ int i,j; srand(time(NULL)); for(i=0;i<taille;i++){ tab[i] = rand()%(NB_VALEURS); printf("%d ", tab[i]); }} int main() { int code[TAILLE]; CodeAlea(code,TAILLE); return 0; }</ital>
Mais, comment avoir un code avec des nombres différents ?
J'ai essayé de faire ça :
int i,j,l=0; srand(time(NULL)); <bold>/*Génération du code de 4 nombres*/</bold> for(i=0;i<taille;i++){ tab[i] = rand()%(NB_VALEURS);} <bold>/*Parcours du tableau*/</bold> for(i=l;i<(taille-1);i++){ for(j=l+1;j<taille;j++){ if(tab[i] == tab[j]){ tab[j] = rand()%(NB_VALEURS); <bold>/*On redonne une valeur à tab[j]*/</bold> l=0; <bold>/*On parcours le tableau depuis le début*/</bold> }}} <bold>/*Affichage du code*/</bold> for(i=0;i<taille;i++){ printf("%d ",tab[i]); }}
Mais, ça ne fonctionne pas. Pouvez-vous m'aidez ?
Merci
A voir également:
- Generateur code 4 chiffres
- Transmath 3eme exercice ✓ - Forum Études / Formation High-Tech
- Corrigé d'un exercice du livre transmaths 3e - Forum Loisirs / Divertissements
- Fleur d'encre 5eme corrigé exercice - Forum PDF
- Corrigés 350 exercices niveau moyen ✓ - Forum Loisirs / Divertissements
- Livre du professeur 5eme fleur d'ancre ✓ - Forum PDF
4 réponses
Test
for(nb nombre => 4fois){ bool tmp = false; do{ //générer un nombre rand //Boucle pour test si le nombre est dans le tableau //si oui on fait rien //si non on passe tmp = true et on ajoute le nombre dans le tableau à la case n correspondant à n itération du for }while(!tmp); }
Je pense avoir réussi. J'ai effectué plusieurs tests et il semblerait que j'ai des valeurs différentes à chaque test.
J'ai un peu modifié votre programme.
Voici ce que j'ai fait :
Merci de votre aide
J'ai un peu modifié votre programme.
Voici ce que j'ai fait :
void Code(int tab[],int taille){ int i,j,tmp=0; srand(time(NULL)); int nb = rand()%(NB_VALEURS); tab[0] = nb; for(i=1;i<taille;i++){ while(!tmp){ nb = rand()%(NB_VALEURS); for(j=0;j<i;j++){ if(nb != tab[j]){ tmp = 1; }else{ tmp = 0; j=i; } } if(tmp==1){ tab[i] = nb; } } tmp = 0; } for(i=0;i<taille;i++){ printf("%d ",tab[i]); } }
Merci de votre aide
cela devrait marcher, même si on peut faire plus simple.
autrement, pour faire original, tu pourrais utiliser strchr() accessible par string.h...
http://www.cplusplus.com/reference/cstring/strchr/
... vu que tes nombres sont compris de 0 à 9, et qu'ils tiennent dans un char, tu pourrais mettre un petit "twist" dans ton code et les stocker dans une chaîne C (un tableau de 5 char terminé par '\0'), en générant des nombres aléatoires tirés sur le range des codes ASCII des chiffres, et ton code tiendrait en quelques lignes et pourrait même être plus approprié si, en fait, tu veux juste utiliser ces numéros pour afficher le code à 4 chiffres :-D
Dal
autrement, pour faire original, tu pourrais utiliser strchr() accessible par string.h...
http://www.cplusplus.com/reference/cstring/strchr/
... vu que tes nombres sont compris de 0 à 9, et qu'ils tiennent dans un char, tu pourrais mettre un petit "twist" dans ton code et les stocker dans une chaîne C (un tableau de 5 char terminé par '\0'), en générant des nombres aléatoires tirés sur le range des codes ASCII des chiffres, et ton code tiendrait en quelques lignes et pourrait même être plus approprié si, en fait, tu veux juste utiliser ces numéros pour afficher le code à 4 chiffres :-D
Dal
comme cela :
le plus long, c'est de taper les #include ;-D ... la taille du tableau est gérée toute seule par le premier while, qui vérifie si on arrive au caractère NULL de la chaîne C, qui est donc alors complète. La chaîne elle même est initialisée avec 4 char quelconques de façon à ce que le caractère NULL se trouve en 5ème et dernière position (fait tout seul à la déclaration), ces char étant écrasés au fur et à mesure. Cela permet de mettre de l'intelligence dans les données, qui autrement devrait se retrouver sous forme de code.
Bien sûr, c'est du code acrobatique, et je doute qu'il plaise à un enseignant (c'est d'ailleurs pourquoi je le poste même s'il s'agit d'un exercice que tu dois faire), mais j'avais envie de faire ma proof of concept là pour illustrer ma remarque ;-)
Dal
P.S. : à propos de #include, tu avais omis
#include <stdio.h> #include <stdlib.h> #include <time.h> #include <string.h> int main(void) { char code[5] = "XXXX"; char ch; int n = 0; srand(time(NULL)); while (code[n++]) { while (strchr(code, ch = rand() % 10 + '0')) ; /* ensure ch is not found in code */ code[n-1] = ch; } printf("Code = %s\n", code); return 0; }
le plus long, c'est de taper les #include ;-D ... la taille du tableau est gérée toute seule par le premier while, qui vérifie si on arrive au caractère NULL de la chaîne C, qui est donc alors complète. La chaîne elle même est initialisée avec 4 char quelconques de façon à ce que le caractère NULL se trouve en 5ème et dernière position (fait tout seul à la déclaration), ces char étant écrasés au fur et à mesure. Cela permet de mettre de l'intelligence dans les données, qui autrement devrait se retrouver sous forme de code.
Bien sûr, c'est du code acrobatique, et je doute qu'il plaise à un enseignant (c'est d'ailleurs pourquoi je le poste même s'il s'agit d'un exercice que tu dois faire), mais j'avais envie de faire ma proof of concept là pour illustrer ma remarque ;-)
Dal
P.S. : à propos de #include, tu avais omis
#include <stdlib.h>dans ton code posté initialement (qui est nécessaire à srand et rand)
hop, un petit changement : on peut faire l'incrémentation postfixe de
Dal
navant de boucler, plutôt qu'au test, pour éviter la soustraction :
#include <stdio.h> #include <stdlib.h> #include <time.h> #include <string.h> int main(void) { char code[5] = "XXXX"; char ch; int n = 0; srand(time(NULL)); while (code[n]) { while (strchr(code, ch = rand() % 10 + '0')) ; /* ensure ch is not found in code */ code[n++] = ch; /* store it, then increment n */ } printf("Code = %s\n", code); return 0; }
Dal
Non, il subsiste une erreur dans ton code.
A la fin de la boucle, tu regardes si tmp vaut 1 ou 0. Or tu initialises tmp à chaque tour, donc ton test ne vérifie que le fait que la dernière vérification est bonne. Il y a donc des lignes en trop!
A la fin de la boucle, tu regardes si tmp vaut 1 ou 0. Or tu initialises tmp à chaque tour, donc ton test ne vérifie que le fait que la dernière vérification est bonne. Il y a donc des lignes en trop!
void Code(int tab[],int taille){ srand(time(NULL)); for( int i = 0 ; i < taille ; ++i ) { int nb = rand() % (NB_VALEURS); int j; for ( int j = 0 ; j < i ; ++j ) { // comparer aux precedents if ( nb == tab[j] ) // deja choisi break; // inutile de continuer } if ( j == i ) // tous on passe le test avec brio tab[i] = nb; else // ce nb ne vas pas, essayer un autre --i; // astuce => le prochain sera le même indice : on refait } }
donc ton test ne vérifie que le fait que la dernière vérification est bonne.
Je ne pense pas.
"tmp" est mis à "faux" dans le while dès qu'une répétition est trouvée, et on sort de la boucle "for j" pour retenter le tirage sans ajouter ce chiffre, comme la vérification est faite par itération chiffre par chiffre, on teste effectivement toutes les positions.
"tmp" est forcé à "vrai" dans le while s'il n'y a pas de répétition, le test étant fait pour chaque chiffre, pas que pour le dernier. Donc, pour que "tmp" vaille "vrai" à la fin de la boucle "for j", et vu que les deux branches du if sont alternatives et exclusives, il faut qu'il n'y ait eu aucun chiffre répété depuis l'index 0 jusqu'à l'index courant i.
le
.. je peux me tromper, mais je n'arrive pas à imaginer un cas où la vérification échouerait.
Il y a donc des lignes en trop!
oui :-)
Dal
Je ne pense pas.
for(i=1;i<taille;i++){ while(!tmp){ nb = rand()%(NB_VALEURS); for(j=0;j<i;j++){ if(nb != tab[j]){ tmp = 1; }else{ tmp = 0; j=i; } } if(tmp==1){ tab[i] = nb; } } tmp = 0; }
"tmp" est mis à "faux" dans le while dès qu'une répétition est trouvée, et on sort de la boucle "for j" pour retenter le tirage sans ajouter ce chiffre, comme la vérification est faite par itération chiffre par chiffre, on teste effectivement toutes les positions.
"tmp" est forcé à "vrai" dans le while s'il n'y a pas de répétition, le test étant fait pour chaque chiffre, pas que pour le dernier. Donc, pour que "tmp" vaille "vrai" à la fin de la boucle "for j", et vu que les deux branches du if sont alternatives et exclusives, il faut qu'il n'y ait eu aucun chiffre répété depuis l'index 0 jusqu'à l'index courant i.
le
tmp = 0;est correctement mis dehors du while avant d'attaquer la prochaine position de chiffre à tirer, pour que le while soit exécuté à la prochaine itération de "for i".
.. je peux me tromper, mais je n'arrive pas à imaginer un cas où la vérification échouerait.
Il y a donc des lignes en trop!
oui :-)
Dal
ce n'est pas le mien, c'est celui de WhiteTiger851 (l'OP).
le mien est là https://forums.commentcamarche.net/forum/affich-34521511-exercice-generer-un-code-de-4-nombres-aleatoires-differentes#5 avec 2 boucles while tenant sur 4 lignes :-)
Dal
le mien est là https://forums.commentcamarche.net/forum/affich-34521511-exercice-generer-un-code-de-4-nombres-aleatoires-differentes#5 avec 2 boucles while tenant sur 4 lignes :-)
Dal