Tout d'abord, je suis ravi d'intégrer votre communauté de codeurs !
Ensuite, je commence tout juste à apprendre la programmation en langage C via les cours en ligne d'OpenClassrooms, aussi, on ne se moque pas (pas trop)
Dans le code ci-dessous, à l'intérieur du if () (que j'ai mis en gras), j'aimerais pouvoir programmer la condition "si l'utilisateur entre un nombre qui n'est pas compris entre MIN et MAX, ou s'il entre tout autre caractère qu'un chiffre (sauf le point), alors, on printf ("Ce n'est pas ce qu'on te demande ! Recommence !\n\n", et on recommence la boucle".
int main() { const int MAX = 100, MIN = 1; double Reponse = 0; int Compteur = 0; int continuerPartie = 0;
srand(time(NULL)); int nombreMystere = (rand() % (MAX - MIN + 1)) + MIN;
do { Compteur++; printf("Quel est le nombre mystere ? "); scanf ("%lf", &Reponse); printf ("\n");
if () { printf ("C'est pas ce qu'on te demande ! Recommence !\n\n"); Compteur -= 1; continuerPartie = 1; } else { do { if (Reponse < nombreMystere) printf("C'est plus ! Essaye encore !\n\n"); else if (Reponse > nombreMystere) printf("C'est moins ! Essaye encore !\n\n"); else { if (Compteur == 1) printf ("Bien joue ! Tu as trouve la reponse en 1 coup !\n\n"); else printf ("Bien joue ! Tu as trouve la reponse en %d coups !\n\n", Compteur); printf ("Veux-tu refaire une partie ?\n"); printf ("Tape 1 pour 'oui', 0 pour 'non' : "); scanf ("%d", &continuerPartie); printf ("\n"); if (continuerPartie == 1) printf ("Excellent choix, mon poteaux ! T'as l'air d'aimer t'eclater a des trucs de merde !\n\n"); else printf ("Tant pis pour toi ! Adieu et bon vent !\n"); } } while (Reponse != nombreMystere); } } while (continuerPartie == 1); return 0; }
1) Utilises le bouton code </> du forum pour poster ton code.
2) Avant de s'occuper du if, il faudrait que le reste fonctionne : la saisie du nombre mystère n'est pas dans la bonne boucle ! idem pour la saisie de continuer partie.
Pour la condition "si il n'entre pas un nombre compris entre MIN et MAX", ça peut aussi se traduire par :
//Si reponse est strictement inferieur à MIN ou reponse strictement supérieur à MAX.
(je te laisse réfléchir, et si t'y arrives vraiment pas, on te dira comment faire :))
Ensuite, pour "s'il entre tout autre caractère qu'un chiffre, sauf le point", et bien, il me semble que lorsque tu as un
scanf("%d", &nombre);
et que l'utilisateur saisit
console : Quel est le nombre ?
utilisateur : Oh, bonjour twâ, je suis en vacance, youpi !
il aura droit à une un plantage de l'application (il me semble que c'est une tonne de fois "Quel est le nombre, qui s'affiche à l'infini")
Ca, je ne sais pas comment tu peux faire à ce stade là du cours, attend de voir les chaines de caractères...
(Après, je suis encore plutôt un débutant, donc il y a peut-être une autre solution ...)
edit: comme l'a dit rouloude, le programme ne fonctionne pas, tu devrais essayer le programme au fur et à mesure, pour voir si tout fonctionne correctement.
- Edité par Le_Wasabi_Ca_Pik' 27 juin 2019 à 18:54:37
"Il faut toujours viser la lune, car même en cas d'échec on atterit dans les étoiles". -Oscar Wilde-
J'arrive avec un code tout cuit parce que ça fait deux jours que je planche sur le même problème que toi ; donc, je vais faire mon rat et profiter de ton sujet pour demander l'avis de personnes plus expérimentées.
[Note à ceux qui s'y connaissent : j'ai bien tenté d'utiliser isdigit, mais cette fonction ne marche définitivement pas chez moi... ]
#include <stdio.h>
#include <stdlib.h>
void viderBuffer(void)
{
int c = 0;
while (c != '\n' && c != EOF)
{
c = getchar();
}
}
int main (void)
{
int min = 0, max = 100;
int nombreChoisi = 0; //Nombre choisi par le joueur.
int verifNombre = 0; //Pour vérifier si nombreChoisi est bien un nombre
puts("Choisissez un nombre entre 0 et 100");
verifNombre = scanf("%4d", &nombreChoisi);
viderBuffer();
while ((verifNombre != 1) || ((nombreChoisi < min) || (nombreChoisi > max)))
{
puts("Ce n'est pas ce qu'on te demande. Recommence !");
verifNombre = scanf("%4d", &nombreChoisi);
viderBuffer();
}
puts("Le nombre entré est bien valable.");
return 0;
}
- void viderBuffer(void) : pour la faire brève, cette fonction permet de "nettoyer" les saisies au clavier. J'avais oublié de la mettre au début et j'ai eu une sale surprise (boucle infinie). Je ne te l'explique pas maintenant, car elle ne correspond pas à ce que tu demandes et ça risquerait de faire trop d'informations en même temps.
- puts : fonctionne comme printf tant qu'on n'a pas besoin de mettre de format (%d, %ld, etc.).
- verifNombre = scanf("%4d", &nombreChoisi) :
%4d : permet de limiter la saisie au clavier pour éviter les dépassements de mémoire. Le chiffre 4 correspond à 3 nombres (pour permettre au joueur d'entrer le chiffre 100 s'il le veut) + 1 caractère spécial ajouté automatiquement qui permet de savoir où se termine la saisie entrée par le joueur (si je ne me trompe pas).
quand scanf fait une ou plusieurs conversions (ici, une seule : entre %d et &nombreChoisi), il retourne le nombre de conversions réussies. Il réussit si l'entrée de l'utilisateur correspond au format attendu (ici : "%d"). verifNombre va stocker le nombre de conversions réussies. Ici, si l'utilisateur entre un chiffre/nombre, celui-ci va correspondre à %d et scanf va retourner 1, donc verifNombre vaudra 1. Si l'utilisateur entre n'importe quoi d'autre, scanf retournera 0, donc verifNombre vaudra 0.
Il y a aussi une histoire de priorité d'opérateurs assez crasse (je trouve), alors je m'en débarrasse en mettant tout simplement des parenthèses partout : https://www.commentcamarche.net/contents/115-langage-c-les-operateurs (le tableau des priorités est tout en bas de l'article).
SALOU TOU Lé MONDE ! (pour paraphraser le Dr Nick Riviera )
Je vois que ce p'tit sujet fait quelques émules. C'est cool, j'apprends plein de trucs
Mon premier code fonctionnait bien lorsque je l'ai publié... J'ai du faire une erreur de copier/coller (la honte pour un futur codeur). :/
Grenade 90, tes astuces • verifNombre = scanf("%4d", &nombreChoisi); et • viderBuffer (); m'ont pas mal sauvé ! En tous cas des bugs inhérents à une saisie intempestive de tout autre caractère qu'un chiffre. Malheureusement, si cela fonctionne bien lorsqu'on ne rentre que des caractères, ou des caractères suivis de chiffres, ça continue de bugger lorsqu'on rentre des chiffres suivis de caractères. Je vous laisse tester avec le code ci-joint. Si vous avez une astuce pour palier cette défaillance, je suis preneur !
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
void viderBuffer(void)
{
int c = 0;
while (c != '\n' && c != EOF)
c = getchar();
}
int main()
{
int MIN = 0, MAX = 0;
double Reponse = 0;
int Compteur = 0;
int continuerPartie = 0;
int modeDeJeu = 0;
int nombreMystere = 0;
int niveauDifficulte = 0;
int onYVa = 0;
int verifSaisie = 0;
do
{
printf ("------MODE DE JEU------\n");
printf ("1 . Automatique\n");
printf ("2 . Multijoueur\n");
printf ("-----------------------\n\n");
do
{
do
{
printf ("Quel mode de jeu choisis-tu ? ");
verifSaisie = scanf ("%d", &modeDeJeu);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf ("\n");
if (modeDeJeu == 1)
{
printf ("-----NIVEAUX DE DIFFICULTE-----\n");
printf ("1 . Facile\n");
printf ("2 . Intermediaire\n");
printf ("3 . Difficile\n");
printf ("4 . Personnalise\n");
printf ("------------------------------\n\n");
do
{
do
{
printf ("Quel niveau de difficulte choisis-tu ? ");
verifSaisie = scanf ("%d", &niveauDifficulte);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf ("\n");
if (niveauDifficulte == 1)
{
MIN = 1;
MAX = 100;
printf ("-----------------NIVEAU 1 : FACILE------------------\n");
printf ("Le nombre a trouver se situe entre 1 et 100 !\n");
printf ("-----------------------------------------------------\n\n");
}
if (niveauDifficulte == 2)
{
MIN = 1;
MAX = 1000;
printf ("---------------NIVEAU 2 : INTERMEDIAIRE---------------\n");
printf ("Le nombre a trouver se situe entre 1 et 1000 !\n");
printf ("------------------------------------------------------\n\n");
}
if (niveauDifficulte == 3)
{
MIN = 1;
MAX = 10000;
printf ("-----------------NIVEAU 3 : DIFFICILE-----------------\n");
printf ("Le nombre a trouver se situe entre 1 et 10000 !\n");
printf ("------------------------------------------------------\n\n");
}
if (niveauDifficulte == 4)
{
printf ("----------------NIVEAU 4 : PERSONNALISE---------------\n");
printf ("Determine toi-meme les limites de l'intervalle !\n");
printf ("------------------------------------------------------\n\n");
do
{
printf ("Nombre minimum = ");
verifSaisie = scanf ("%d", &MIN);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
do
{
printf ("Nombre maximum = ");
verifSaisie = scanf ("%d", &MAX);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf ("\n");
printf ("Le nombre a rechercher se situe entre %d et %d !\n\n", MIN, MAX);
}
if (niveauDifficulte != 1 && niveauDifficulte != 2 && niveauDifficulte != 3 && niveauDifficulte != 4)
{
printf ("On t'a demande de choisir entre les 4 propositions, connard ! Recommence !\n\n");
viderBuffer();
}
srand(time(NULL));
nombreMystere = (rand() % (MAX - MIN + 1)) + MIN;
printf ("---------------------ES-TU PRES A T'ECLATER COMME UNE BEEETE ???---------------------\n");
printf ("1 . O oui, je le veux !\n");
printf ("2 . Par pitie, arretez-ca tout de suite, j'en peux deja plus de ce jeu de MEEERDE !\n");
printf ("-------------------------------------------------------------------------------------\n\n");
do
{
do
{
printf ("On y va ? : ");
verifSaisie = scanf ("%d", &onYVa);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf ("\n");
if (onYVa == 2)
{
printf ("ARGH ! Tant pis pour toi ! Adieu et bon vent !\n\n");
return 1;
}
else if (onYVa != 2 && onYVa != 1)
{
printf ("On t'a demande de choisir entre 1 et 2, abruti ! Recommence !\n\n");
viderBuffer();
}
} while (onYVa != 1 && onYVa != 2);
} while (niveauDifficulte != 1 && niveauDifficulte != 2 && niveauDifficulte != 3 && niveauDifficulte != 4);
}
if (modeDeJeu == 2)
{
printf ("-----------------------MODE MULTIJOUEUR-----------------------\n");
printf ("Demande a ton poteau-copinou de choisir le nombre mystere !\n");
printf ("--------------------------------------------------------------\n\n");
do
{
printf ("Choisis le nombre mystere : ");
verifSaisie = scanf ("%d", &nombreMystere);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf ("\n");
}
if (modeDeJeu != 1 && modeDeJeu != 2)
{
printf ("On t'a demande de choisir entre 1 et 2 ! Tu sais lire ? Recommence !\n\n");
viderBuffer();
}
} while (modeDeJeu != 1 && modeDeJeu != 2);
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("************************************************************\n");
printf ("******************* DEBUT DU SUPER JEU *******************\n");
printf ("*************** A TOI DE DEVINER HIHIHI !!! ***************\n\n");
do
{
Compteur++;
do
{
printf("Quel est le nombre mystere ? ");
verifSaisie = scanf ("%lf", &Reponse);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf ("\n");
if (Reponse < nombreMystere)
printf ("C'est plus ! Essaye encore !\n\n");
else if (Reponse > nombreMystere)
printf ("C'est moins ! Essaye encore !\n\n");
else
{
if (Compteur == 1)
printf ("Bien joue ! Tu as trouve la reponse en 1 seul coup !\n\n");
else
printf ("Bien joue ! Tu as trouve la reponse en %d coups !\n\n", Compteur);
printf ("----NOUVELLE PARTIE ?---\n");
printf ("1 . Oui\n");
printf ("2 . Non\n");
printf ("------------------------\n\n");
do
{
do
{
printf ("Veux-tu rejouer ? ");
verifSaisie = scanf ("%d", &continuerPartie);
if (verifSaisie != 1)
{
printf ("\nCe n'est pas un chiffre ou un nombre ! Recommence !\n\n");
viderBuffer();
}
} while (verifSaisie != 1);
printf("\n");
if (continuerPartie == 1)
printf ("Tu as choisi de REJOUER ! Excellent choix, mon poteaux ! T'as l'air d'aimer t'eclater a des trucs de merde !\n\n");
else if (continuerPartie == 2)
printf ("Tu as choisi de TE CASSER ! Tant pis pour toi ! Adieu et bon vent !\n\n");
else
printf ("On t'a demande de choisir entre 1 et 2 ! Recommence !\n\n");
} while (continuerPartie != 1 && continuerPartie != 2);
}
} while (Reponse != nombreMystere);
} while (continuerPartie == 1);
return 0;
}
Je n'avais même pas pensé à tester les combinaisons de chiffres et lettres...
Mais quand j'ai testé, mon code s'est révélé quand même pas mal solide : si tu entres un chiffre suivi d'une lettre, la lettre sera simplement ignorée. Par exemple, si tu entres "6N", le programme va juste prendre en compte "6" (tu peux t'en assurer à l'aide d'un printf), ce qui fait que la réponse est considérée comme valable. Ceci dit, la réponse de l'utilisateur est tronquée ; s'il ne s'en rend pas compte, il pourra penser que le programme fait des bêtises (alors qu'il ne fait que rattraper les siennes...). Je cherche une solution, mais dis-moi si tu trouves un truc de ton côté.
Fvirtman : merci pour l'astuce de "inverser" la condition.
Après, si l'utilisateur se plante, ne lit pas bien les consignes, fait une faute de frappe etc., c'est son problème...
Mais notre problème à nous en tant que programmeurs, c'est que, lorsque l'utilisateur écrit des chiffres suivis de lettres, "verifSaisie" considère à la fois que la saisie est bonne (à cause des chiffres), et à la fois que la saisie est mauvaise (à cause des lettres). Du coup, il passe à la suite en considérant que la saisie est bonne, mais après avoir affiché le message d'erreur disant que la saisie n'est pas bonne (cf image jointe).
Sur l'image, on peut voir qu'il considère que la saisie est bonne (à cause des chiffres), si bien qu'il passe à la suite ("nombre maximum"), et, juste après, il considère que la saisie n'est pas bonne (à cause des lettres), si bien qu'il affiche le message d'erreur ("Ce n'est pas un chiffre ou un nombre ! Recommence !"), pour, au final, considérer quand même que la saisie est bonne et passer à "nombre maximum".
Moi j'dis : il faudrait une fonction qui parcourt la chaine de caractères et qui dise "si, avant le NULL final, je tombe sur un autre caractère qu'un chiffre, alors la saisie n'est pas bonne"...
Pour ma part, je n'ai pas de problème (à mon avis, tu as sans doute oublié de vider le buffer après l'encodage du nombre minimal).
Attention, le code ci-dessous n'est pas du tout optimisé (et puis, il faudrait : préciser à l'utilisateur la valeur maximale possible (notre int n'est pas infini), vérifier que le nombre maximal soit plus grand que le minimal, modifier la demande de saisie en fonction de si c'est la première entrée de l'utilisateur ou s'il a déjà entré un nombre invalide...)
int main (int argc, char* argv[])
{
int min = 0, max = 0;
int verifNombre = 0;
do
{
puts("Choisissez une valeur minimale :");
verifNombre = scanf("%4d", &min);
viderBuffer();
} while (verifNombre != 1);
printf("Nombre minimal = %d\n\n", min);
do
{
puts("Choisissez une valeur maximale :\n\n");
verifNombre = scanf("%4d", &max);
viderBuffer();
} while (verifNombre != 1);
printf("Nombre maximal = %d", max);
return 0;
}
En fait, ici, le programme va, la première fois, ignorer les lettres saisies pour "nombre minimal". Mais si on oublie de vider le buffer, elles restent tout de même dedans. Au deuxième appel de scanf, le joueur n'aura pas la possibilité d'entrer le nombre maximal car le programme ira se servir de lui-même dans les caractères restants du buffer ; puisque dans ton exemple il n'y avait que des lettres, il considérait que l'utilisateur n'avait rien entré de valable pour le nombre maximal. En vidant le buffer, tu enlèves à ton programme la possibilité de self-service dans le scanf et tu règles le problème.
Okéééé ! Un grand merci à toi pour ces limpides explications, Grenade90 !
Limiter la saisie de caractère
× Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
× Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
"Il faut toujours viser la lune, car même en cas d'échec on atterit dans les étoiles". -Oscar Wilde-
"Il faut toujours viser la lune, car même en cas d'échec on atterit dans les étoiles". -Oscar Wilde-
"Il faut toujours viser la lune, car même en cas d'échec on atterit dans les étoiles". -Oscar Wilde-
"Il faut toujours viser la lune, car même en cas d'échec on atterit dans les étoiles". -Oscar Wilde-
Recueil de code C et C++ http://fvirtman.free.fr/recueil/index.html
"Il faut toujours viser la lune, car même en cas d'échec on atterit dans les étoiles". -Oscar Wilde-