Variable mémoire dépassement
truite
-
yg_be Messages postés 23541 Date d'inscription Statut Contributeur Dernière intervention -
yg_be Messages postés 23541 Date d'inscription Statut Contributeur Dernière intervention -
Bonjour! Par curiosité je voulais tester ce qu'il se passerait si j'assignais, à une variable, une valeur plus importante que sa capacité.
Par exemple, si je fais:
avec printf, j'obtiens un nombre totalement différent, quelque chose comme 700 millions et des poussières.
A quoi correspondent ces 700 millions ?
Par ailleurs, si je fais
avec un printf, j'obtiens juste le dernier caractère, c'est-à-dire un
Où va le reste de la variable char qui n'est pas affiché ?
Par exemple, si je fais:
int nombre = 5000000000;
avec printf, j'obtiens un nombre totalement différent, quelque chose comme 700 millions et des poussières.
A quoi correspondent ces 700 millions ?
Par ailleurs, si je fais
char caractere = 'ab';
char caractere = 'abc';
avec un printf, j'obtiens juste le dernier caractère, c'est-à-dire un
bdans le premier cas, et un
cdans le second.
Où va le reste de la variable char qui n'est pas affiché ?
A voir également:
- Variable mémoire dépassement
- Mémoire vive - Guide
- RAM : type, format, CAS, vitesse, tout sur la mémoire vive - Guide
- Nettoyer memoire iphone - Guide
- C'est un secret bien gardé : ce réglage d'expert peut doper les performances de votre PC - Guide
- Impossible de créer le fichier de travail. vérifiez la variable d'environnement temp ✓ - Forum Word
3 réponses
yg_be
Messages postés
23541
Date d'inscription
Statut
Contributeur
Dernière intervention
Ambassadeur
1 584
bonjour, n'hésite pas à montrer toutes tes instructions, ne nous laisse pas deviner comment tu fais appel à printf.
Bonsoir,
Normal
Voila les déclaration en C
Bool 0 1
signed char -127 127
unsigned char 0 255
short -32 767 32 767
unsigned short 0 65 535
int -32 767 32 767
unsigned int 0 65 535
long -2 147 483 647 2 147 483 647
unsigned long 0 4 294 967 295
long long -9 223 372 036 854 775 807 9 223 372 036 854 775 807
unsigned long long 0 18 446 744 073 709 551 615
float -1 × 1037 1 × 1037
double -1 × 1037 1 × 1037
long double -1 × 1037 1 × 1037
Pour votre variable la déclarer en unsigned long long
Pour Char 1 Caractère pas plus
i
Pour une chaine de caractères
Pour le fun
Normal
Voila les déclaration en C
Bool 0 1
signed char -127 127
unsigned char 0 255
short -32 767 32 767
unsigned short 0 65 535
int -32 767 32 767
unsigned int 0 65 535
long -2 147 483 647 2 147 483 647
unsigned long 0 4 294 967 295
long long -9 223 372 036 854 775 807 9 223 372 036 854 775 807
unsigned long long 0 18 446 744 073 709 551 615
float -1 × 1037 1 × 1037
double -1 × 1037 1 × 1037
long double -1 × 1037 1 × 1037
Pour votre variable la déclarer en unsigned long long
Pour Char 1 Caractère pas plus
i
nt main(int argc, char *argv[]) { char lettre = 'A'; printf("%c\n", lettre); return 0; }
Pour une chaine de caractères
int main(int argc, char *argv[]) { char chaine[] = "Salut"; // La taille du tableau chaine est automatiquement calculée printf("%s", chaine); return 0; }
Pour le fun
int longueurChaine(const char* chaine); int main(int argc, char *argv[]) { char chaine[] = "Salut"; int longueur = 0; longueur = longueurChaine(chaine); printf("La chaine %s fait %d caracteres de long", chaine, longueur); return 0; } int longueurChaine(const char* chaine) { int nombreDeCaracteres = 0; char caractereActuel = 0; do { caractereActuel = chaine[nombreDeCaracteres]; nombreDeCaracteres++; } while(caractereActuel != '\0'); // On boucle tant qu'on n'est pas arrivé à l'\0 nombreDeCaracteres--; // On retire 1 caractère de long pour ne pas compter le caractère \0 return nombreDeCaracteres; }
CHAR(n) est un type de données qui respecte de la longueur dont n caractères stockée même si la longueur du texte est inférieure à n, il y aura alors un remplissage à blanc.
Exemple :
« toto » en CHAR(12) donne :
"toto "
VARCHAR(n) est un type de données de longueur variable avec au maximum n caractères stockée + stockage de la longueur du texte (en général sur 2 octets) et pas de remplissage à blanc.
Exemple « toto » en VARCHAR(12) donne :
04"toto"
AVANTAGES / INCONVÉNIENTS :
VARCHAR économise de l’espace si la longueur des données peut être grande et la taille du texte très fluctuante. Or plus on économise l’espace meilleures seront les performances .
Mais si la données est voisine de la taille maximale ou fais toujours la taille maximale, alors avec les 2 octets pour stocker la taille c’est le contraire qui se produit.
Par exemple pour un code postal, c’est stupide car il y aura toujours 5 caractères (en France) => VARCHAR = 7 octets, CHAR = 5 octets
En sus, la recherche d’une colonne VARCHAR est plus complexe que la recherche d’une colonne CHAR au sein de la ligne composant la table. Son accès est donc plus lent, car il faut parcourir toutes les colonnes précédentes du fait de la longueur variable. Alors qu’avec une longueur fixe, il suffit de calculer l’offset par rapport au début de la ligne pour trouver immédiatement l’emplacement du premier caractère de la colonne de type CHAR (en fait pour optimiser les accès aux données, la plupart des SGBDR constituent les lignes des tables avec les colonnes de taille fixe en premier et les colonnes de taille variable en dernier de façon à ce que le repérage des colonnes de type fixe soit immédiat.
Exemple complet de manipulations de variables
...
Exemple :
« toto » en CHAR(12) donne :
"toto "
VARCHAR(n) est un type de données de longueur variable avec au maximum n caractères stockée + stockage de la longueur du texte (en général sur 2 octets) et pas de remplissage à blanc.
Exemple « toto » en VARCHAR(12) donne :
04"toto"
AVANTAGES / INCONVÉNIENTS :
VARCHAR économise de l’espace si la longueur des données peut être grande et la taille du texte très fluctuante. Or plus on économise l’espace meilleures seront les performances .
Mais si la données est voisine de la taille maximale ou fais toujours la taille maximale, alors avec les 2 octets pour stocker la taille c’est le contraire qui se produit.
Par exemple pour un code postal, c’est stupide car il y aura toujours 5 caractères (en France) => VARCHAR = 7 octets, CHAR = 5 octets
En sus, la recherche d’une colonne VARCHAR est plus complexe que la recherche d’une colonne CHAR au sein de la ligne composant la table. Son accès est donc plus lent, car il faut parcourir toutes les colonnes précédentes du fait de la longueur variable. Alors qu’avec une longueur fixe, il suffit de calculer l’offset par rapport au début de la ligne pour trouver immédiatement l’emplacement du premier caractère de la colonne de type CHAR (en fait pour optimiser les accès aux données, la plupart des SGBDR constituent les lignes des tables avec les colonnes de taille fixe en premier et les colonnes de taille variable en dernier de façon à ce que le repérage des colonnes de type fixe soit immédiat.
Exemple complet de manipulations de variables
#define taille_tableau 10 //Défini la taille du tableau des structures clients .............. définition d'une structure nommé enr struct enr { char code[20]; char matiere[30]; float note; }; struct enr fiche1; // décalaration d'une variable fiche1 de type structure enr struct enr tablecode[20]; // un tableau de structure de type enr struct enr *ptr; // un pointeur vers la structure enr .............. définition d'une structure nommé client //-- la structure CLIENT struct client { char ref[10+1]; char nom[20+1]; char prenom[20+1]; char adresse[40+1]; char cp[5+1]; char ville[15+1]; char tel[10+1]; }; //------Tableau de structure CLIENT struct client tab_client[taille_tableau]; // variable globale compteur du nombre de client dans la base int nbre_client=0; // structure de données comme paramétre d'entrée de la fonctione crire_client() void ecrire_client(struct client tmp) // Déclaration de la fonction Saisie des clients void saisie_client(); //Saisie des clients void affiche_client(); //Affiche les clients ... ... 2. Accès aux membre de la structure en C/C++ Un membre d'une structure est accédé par (nom_variable.nom_membre). Un membre d'une structure peut également être accédé par l'intermédiaire d'un pointeur (nom_pointeur->nom.membre). ........... Voir déclaration de structure plus haut struct enr *ptr; struct enr fiche1; int main() { .......................... Accès aux membre de la structure par une variable fiche1................. fiche1.note = 15.5; strpcy(fiche1.code, "MAT145"); strpcy(fiche1.matiere, "Francais"); printf("%s \n",fiche1.matiere); ... ........................... Accès aux membre de la structure par un pointeur ................... ptr = &fiche1 /* mettre l'adresse de fiche1 dans le pointeur ptr */ ptr->note = 18.5; strcpy(ptr->code,"Laurent"); strpcy(ptr->matiere, "Maths"); printf("%s %f \n",ptr->matiere, ptr->note); ... ...........Accès aux membre de la structure par des fonctions. ................... ....... // appel fonction saisie de donneés client ; saisie_client(); // saisie un premier client gotoxy(20,47); system("pause"); saisie_client(); // saisie un 2 client affiche_client() // affiche la liste des clients getch(); return 0; } // fin programme principal ...... // *****Saisie de données CLIENT***** void saisie_client() { struct client tmp_client; //Déclaration de la structure temporaire client char tel[20]; int x=25; // coordonnée de la Ligne x y int y=13; system("cls"); gotoxy(27,3); printf("- SAISIR UNE FICHE CLIENT -"); fflush(stdin); //On vide la mémoire tampon gotoxy(x,y); printf("Reference : "); gets(tmp_client.ref); gotoxy(25,47); printf(" "); gotoxy(x,y+3); printf("Nom : "); gets(tmp_client.nom); gotoxy(x,y+6); printf("Prenom : "); gets(tmp_client.prenom); gotoxy(x,y+9); printf("Adresse : "); gets(tmp_client.adresse); gotoxy(x,y+12); printf("Code postal : "); gets(tmp_client.cp); gotoxy(x,y+15); printf("Ville : "); gets(tmp_client.ville); gotoxy(x,y+18); printf("Telephone : "); gets(tel); strcpy(tmp_client.tel,tel); //On copie la variable tel dans la structure temporaire // fonction ecrire_client() //On écrit dans la base. Pour cela on envoi la structure temporaire de CLIENT ecrire_client(tmp_client); } ..... ************************************** *****Enregistre les données CLIENT***** // une structure de données comme paramètre de la fonction ecrire_client() **************************************/ void ecrire_client(struct client tmp) { //Ecrit les données de la structure temporaire passé en paramètre (tmp) // dans la structure réelle de la base strcpy(tab_client[nbre_client].ref,tmp.ref); strcpy(tab_client[nbre_client].nom,tmp.nom); strcpy(tab_client[nbre_client].prenom,tmp.prenom); strcpy(tab_client[nbre_client].adresse,tmp.adresse); strcpy(tab_client[nbre_client].cp,tmp.cp); strcpy(tab_client[nbre_client].ville,tmp.ville); strcpy(tab_client[nbre_client].tel,tmp.tel); gotoxy(23,40);textcolor(10);printf("Le client a ete ajoute dans la base"); nbre_client++; //Ajout d'un client dans la base } ............ *****Afficher les clients***** parcourir un tableau de structure de données **************************** void affiche_client() { int i; //Compteur de boucle int x=20; //Represente la coordonnée de la Ligne int y=15; //Represente la coordonnée de la Colonne for(i=0; i< nbre_client;i++) { system("cls"); gotoxy(28,3); printf("- AFFICHER LES CLIENTS -"); gotoxy(x,y); printf("Reference : %s ",tab_client[i].ref); gotoxy(x,y+3); printf("Nom : %s ",tab_client[i].nom); gotoxy(x,y+6); printf("Prenom : %s ",tab_client[i].prenom); gotoxy(x,y+9); printf("Adresse : %s ",tab_client[i].adresse); gotoxy(x,y+12); printf("Code postal : %s ",tab_client[i].cp); gotoxy(x,y+15); printf("Ville : %s ",tab_client[i].ville); gotoxy(x,y+18); printf("Telephone : %s ",tab_client[i].tel); gotoxy(30,40); printf("Client %d sur %d",i+1,nbre_client); gotoxy(20,47); system("pause"); } } //fin affiche_client ..................
...
j'ai fait un
et le nombre exact est 705032704
(j'utilise visual studio 2019, pour le compilateur je n'en sais pas plus)
Visual studio ne dispose pas de compilateur C.
Voir ce message de Dalfb https://forums.commentcamarche.net/forum/affich-37065516-visual-studio#4 (comme la discussion entière ne fait que 5 messages, je t'invite à la lire complètement).
D'autre part, pour du "vrai" C, voir cet article au chapitre "Débordement" https://fr.wikibooks.org/wiki/Programmation_C/Types_de_base#D%C3%A9bordement