Contenu | Rechercher | Menus

Annonce

Si vous avez des soucis pour rester connecté, déconnectez-vous puis reconnectez-vous depuis ce lien en cochant la case
Me connecter automatiquement lors de mes prochaines visites.

À propos de l'équipe du forum.

#1 Le 22/05/2017, à 11:05

DonutMan75

[RESOLU] [C] Allocation libération de mémoire en C

Bonjour à tous,
mon précédent fil de discussion sur la fonction getsubopt() m'a permis de réaliser que j'étais un peu faiblard concernant les pointeurs en C.
Pourriez-vous me donner votre avis sur ce petit exercice didactique que j'ai imaginé ?

Objectif :
- Créer dynamiquement un pointeur sur un tableau de caractère contenant les lettres de l'alphabet A, B, C,... , Z
- Afficher l'adresse et la valeur des 10 premiers caractères de ce tableau
- Modifier le pointeur initial pour ignorer les 5 premiers caractères du tableau
- Libérer proprement la mémoire de tout ce petit monde...

Voici ce que j'ai fait... Qu'en pensez-vous ? J'ai utilisé un pointeur de pointeur afin de rendre licite l'instruction c = *c +5...

Merci d'avance pour vos commentaires et vos avis smile

Donut

#include <stdio.h>
#include <stdlib.h>

int main(void)
{
char **c;
c = malloc(sizeof(char*));
*c = calloc(128, sizeof(char));
*c = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";

fprintf(stdout, "%p --> [%p -> '%s']\n", c, *c, *c);

// Affichage des 10 premières valeurs

int k;
printf("*** PREMIERE BOUCLE ***\n");
for (k=0; k<10; k++)
	{
	fprintf(stdout, "  - %p+%02d = %p --> %c\n", *c, k, *(c)+k, *(*(c)+k));
	}

// Et maintenant on change la valeur pointée par *c pour ignorer les 5 premiers caractères
// Faut-il mettre un free ici pour libérer les zones mémoires stockant les 5 premiers caractères ???
*c = *c+5;
printf("*** SECONDE BOUCLE ***\n");
for (k=0; k<10; k++)
	{
	fprintf(stdout, "  - %p+%02d = %p --> %c\n", *c, k, *(c)+k, *(*(c)+k));
	}

// Liberation de la mémoire
// Ici je sèche complétement
// un free(c) fonctionne mais ne libère pas la zone mémoire stockant la chaîne de caractère si ??
// un free(*c) plante....

Dernière modification par DonutMan75 (Le 22/05/2017, à 22:25)

Hors ligne

#2 Le 22/05/2017, à 12:12

alduc31

Re : [RESOLU] [C] Allocation libération de mémoire en C

Salut,

Oui pas très au point sur les pointeurs en C. Simplement on peut faire comme ça :

#include <stdio.h>
#include <stdlib.h>

int main(void)
{
  int   i;
  char  *c, *p;

  /* allocation du tableau de char */
  c = (char *) calloc(128, sizeof(char));

  /* remplissage des 26 premieres valeurs de A a Z */
  for (i = 0; i < 26; i++)
    c[i] = 'A' + i;

  /* affiche 10 premieres valeurs */
  for (i = 0; i < 10; i++)
    fprintf(stdout,"c[%d] = %c\n",i,c[i]);

  /* p pointe sur la 6ieme valeur du tableau */
  p = c + 5;
  for (i = 0; i < 10; i++)
    fprintf(stdout,"p[%d] = %c\n",i,p[i]);

  /* liberation (c a toujours la valeur retournee par calloc) */
  free(c);

  return 0;
}

Quelques remarques :
1/ indenter le code aide grandement à la lecture (et pas une indentation anarchique)
2/ déclaration de variables en plein milieu de code pas terrible (ton int k)

Je te laisse médité ce bout de code.


Asus UX325EA oled (i5-1135G7,16Go) avec Lunar 23.04 (base xubuntu modifiée)

Hors ligne

#3 Le 22/05/2017, à 13:48

grigouille

Re : [RESOLU] [C] Allocation libération de mémoire en C

Pourquoi des malloc ?

$ cat toto.c
#include <stdio.h>
#include <stdlib.h>

int main(void)
{
        const char *c = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";

        const char *p = c;
        int i = 0;
        for(i = 0 ; i < 10 ; ++i) {
                printf("%d : %c\n", i, *p++);
        }

        printf("\n");

        p+=5;
        for(i = 0 ; i < 10 ; ++i) {
                printf("%d : %c\n", i, *p++);
        }
        return 0;
}
$ gcc -o toto toto.c && ./toto
0 : A
1 : B
2 : C
3 : D
4 : E
5 : F
6 : G
7 : H
8 : I
9 : J

0 : P
1 : Q
2 : R
3 : S
4 : T
5 : U
6 : V
7 : W
8 : X
9 : Y

Debian (xfce) 12
HP LaserJet M1132 MFP

Hors ligne

#4 Le 22/05/2017, à 14:05

DonutMan75

Re : [RESOLU] [C] Allocation libération de mémoire en C

Hello,
merci pour vos réponses, c'est un peu plus clair maintenant smile
Mais en fait, ça m'a permis de préciser mon point de doute.

Quand on écrit :

c = (char *) calloc(128, sizeof(char));

On réserve un espace mémoire contigu permettant de stocker 128 caractères, est-ce exact ?
Et il est correct, je crois, de dire que 'c' est l'adresse mémoire de cet espace et qu'il pointe par définition, sur son premier élément (en l'occurence 'A')

Mais quand je fais

free(c)

Je libère bien l'ensemble de cet espace mémoire (donc les 128 blocs contenant chacun un caractère) ?

Est-il par conséquent possible de supprimer (libérer ?) le premier de ces blocs mémoires et d'avoir c qui pointe vers un bloc mémoire de 128-1=127 éléments ?

Si je comprends bien vos deux exemples, on introduit ici une nouvelle variable p mais l'ensemble des 128 éléments existe toujours en mémoire ?

Merci pour vos éclaircissements smile

Donut

Hors ligne

#5 Le 22/05/2017, à 19:10

alduc31

Re : [RESOLU] [C] Allocation libération de mémoire en C

DonutMan75 a écrit :

Quand on écrit :

c = (char *) calloc(128, sizeof(char));

On réserve un espace mémoire contigu permettant de stocker 128 caractères, est-ce exact ?

Oui.

Et il est correct, je crois, de dire que 'c' est l'adresse mémoire de cet espace et qu'il pointe par définition, sur son premier élément (en l'occurence 'A')

Oui.

Mais quand je fais

free(c)

Je libère bien l'ensemble de cet espace mémoire (donc les 128 blocs contenant chacun un caractère) ?

Oui tout le bloc alloué.

Est-il par conséquent possible de supprimer (libérer ?) le premier de ces blocs mémoires et d'avoir c qui pointe vers un bloc mémoire de 128-1=127 éléments ?

Non on ne peut pas libérer qu'une partie.

Si je comprends bien vos deux exemples, on introduit ici une nouvelle variable p mais l'ensemble des 128 éléments existe toujours en mémoire ?

Oui tant que le free n'est pas fait ou que le programme se termine. La variable p sert à manipuler le pointeur sans toucher à la valeur initiale c nécessaire pour le free.


Asus UX325EA oled (i5-1135G7,16Go) avec Lunar 23.04 (base xubuntu modifiée)

Hors ligne

#6 Le 22/05/2017, à 22:25

DonutMan75

Re : [RESOLU] [C] Allocation libération de mémoire en C

Super, merci beaucoup pour vos toutes vos contributions smile
C'est plus clair pour moi maintenant !

Bonne soirée !

Donut

Hors ligne