IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

 C Discussion :

Différence entre ** et &* ?


Sujet :

C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2009
    Messages
    62
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2009
    Messages : 62
    Par défaut Différence entre ** et &* ?
    Bonjour,

    J'aimerais comprendre pourquoi ce code fonctionne:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    int main(int argc, char ** argv){
            int     n = 0;
            size_t  taille = 0;
            char    *c1;
            char    *c2;
            char    *saveptr;
     
     
            while(getline(&c1, &taille, stdin) != -1){
                    printf("Ligne %d\n", ++n);
                    c2 = strtok_r(c1, "\t ", &saveptr);
     
                    while(c2 != NULL){
                            printf("\t%s\n", c2);
                            c2 = strtok_r(NULL, "\t ", &saveptr);
                    }   
            }   
     
            printf("\nDone\n");
     
            return 0;
    }
    Et celui ci me sort une erreur de segmentation:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    int main(int argc, char ** argv){
            int     n = 0;
            size_t  taille = 0;
            char    *c1;
            char    *c2;
            char    **saveptr;
     
     
            while(getline(&c1, &taille, stdin) != -1){
                    printf("Ligne %d\n", ++n);
                    c2 = strtok_r(c1, "\t ", saveptr);
     
                    while(c2 != NULL){
                            printf("\t%s\n", c2);
                            c2 = strtok_r(NULL, "\t ", saveptr);
                    }   
            }   
     
            printf("\nDone\n");
     
            return 0;
    }
    Sachant que le prototype de strtok_r est:
    char *strtok_r(char *str, const char *delim, char **saveptr);
    Je croyais que un pointeur1 de pointeur2 contenais l'adresse de pointeur2, equivalent a &pointeur2.

  2. #2
    Inactif  


    Homme Profil pro
    Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Inscrit en
    Décembre 2011
    Messages
    9 026
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 32
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Secteur : Enseignement

    Informations forums :
    Inscription : Décembre 2011
    Messages : 9 026
    Par défaut
    Déclarer un pointeur ne suffit pas, il faut aussi allouer l'espace.

    Tu as un char ** mais sur quoi pointe-t-il?

    Lorsque tu utilises ta fonction, il va faire une copie de ton char ** puis il va écrire un pointeur char * dans l'objet pointé par ton char ** or tu n'as pas alloué l'espace pour le char * pointé par ton char **.

  3. #3
    Membre confirmé
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2009
    Messages
    62
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2009
    Messages : 62
    Par défaut
    Ha oui, j'oublie a chaque fois..
    Toutefois, je comprend pas pourquoi le premier code fonctionne du coup, simple coup de chance que la mémoire ne soit pas déjà allouée ?

  4. #4
    Inactif  


    Homme Profil pro
    Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Inscrit en
    Décembre 2011
    Messages
    9 026
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 32
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Secteur : Enseignement

    Informations forums :
    Inscription : Décembre 2011
    Messages : 9 026
    Par défaut
    strtok_r dois allouer l'espace mémoire pour contenir les caractères mais il n'alloue pas le char *.

    Après, en regardant le man, on devrait avoir plus d'informations.

  5. #5
    Membre Expert Avatar de Trademark
    Profil pro
    Inscrit en
    Février 2009
    Messages
    762
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2009
    Messages : 762
    Par défaut
    Salut,

    Comme pour toutes variables, si vous voulez modifier la valeur, il faut alors passer son adresse. Ici le type concerné est char*, en passant son adresse on a un char**.

    Je présume que strtok_r fait quelque chose comme *saveptr = &str[i];. Tu ne pourrais pas mettre à jour saveptr de cette façon si tu passais un char*. Du coup avec ton deuxième code je te laisse imaginer

  6. #6
    Inactif  


    Homme Profil pro
    Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Inscrit en
    Décembre 2011
    Messages
    9 026
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 32
    Localisation : France, Loire (Rhône Alpes)

    Informations professionnelles :
    Activité : Doctorant sécurité informatique — Diplômé master Droit/Économie/Gestion
    Secteur : Enseignement

    Informations forums :
    Inscription : Décembre 2011
    Messages : 9 026
    Par défaut
    Dans son deuxième code saveptr est un char ** et non un char *.

    A par le fait que saveptr ne pointe pas sur un char * alloué, je ne vois pas pourquoi son deuxième code ne marcherait pas.

  7. #7
    Membre confirmé
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2009
    Messages
    62
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Janvier 2009
    Messages : 62
    Par défaut
    Le deuxième code fonctionne si j'alloue de la mémoire pour **saveptr, mais pourquoi l'allocation n'est pas nécessaire si je déclare *saveptr et non **saveptr ?

  8. #8
    Expert confirmé
    Avatar de diogene
    Homme Profil pro
    Enseignant Chercheur
    Inscrit en
    Juin 2005
    Messages
    5 761
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Enseignant Chercheur
    Secteur : Enseignement

    Informations forums :
    Inscription : Juin 2005
    Messages : 5 761
    Par défaut
    c1 devrait être initialisé à NULL avant le premier appel à getline()

    Cf man pages
    ssize_t getline(char **lineptr, size_t *n, FILE *stream);
    ......
    getline() lit une ligne entière dans stream et stocke l'adresse du tampon contenant le texte dans *lineptr. Le tampon se termine par un caractère nul et inclut le caractère « saut de ligne » s'il y en a un.
    Si *lineptr vaut NULL, getline() alloue un tampon pour recevoir la ligne. Ce tampon devra être libéré par le programme utilisateur. (La valeur dans *n est ignorée). Alternativement, avant d'appeler getline(), *lineptr peut contenir un pointeur vers un tampon alloué par malloc(3) et de taille *n octets. Si le tampon n'est pas suffisant pour recevoir la ligne saisie, getline() le redimensionne avec realloc(3), mettant à jour *lineptr et *n comme il se doit.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Différence entre un "bidouilleur" et un Pro ?
    Par christ_mallet dans le forum Débats sur le développement - Le Best Of
    Réponses: 290
    Dernier message: 28/11/2011, 10h53
  2. Différence entre TCP, UDP, ICMP
    Par GliGli dans le forum Développement
    Réponses: 1
    Dernier message: 13/09/2002, 08h25
  3. Différences entre jmp, jz, jnz, etc
    Par christbilale dans le forum Assembleur
    Réponses: 3
    Dernier message: 05/07/2002, 15h09
  4. Réponses: 3
    Dernier message: 07/05/2002, 16h06

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo