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 :

return de double tableau dans une autre fonction


Sujet :

C

  1. #1
    Membre habitué Avatar de awesomeman
    Homme Profil pro
    Étudiant
    Inscrit en
    Octobre 2015
    Messages
    166
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2015
    Messages : 166
    Points : 136
    Points
    136
    Par défaut return de double tableau dans une autre fonction
    Bonsoir ,
    je cherche à savoir comment je peux envoyé dans une autre fonction un double tableau avec toutes les données que comporte celui ci .
    Pour l'instant: - je déclare un double pointeur (char **save) dans une fonction 1 (du meme type que mon save).
    -je malloc , j'insère les donnée dans un tableau save[x][y] , je free.
    -puis je fais :return (save);

    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
    23
    24
    25
    26
    27
    28
    29
    char 	**check(int i, char buffer[2000000], int col)
    {
      char **save;
      int x;
      int y;
     
      x = 0;
      y = 0;
      save = malloc(sizeof(char*) * 100);
      while(buffer[i])
        {
          save[x] = malloc(sizeof(char) * col);
          if (buffer[i] == 'o')
          save[x][y] = 'o';
          else if (buffer[i] == '.')
          save[x][y] = '.';
          if (buffer[i] == 'o' || buffer[i] == '.')
    	y++;
          if (buffer[i] == '\n')
    	{
    	  save[x][y] = '\n';
    	  x++;
    	  y = 0;
    	}
          i++;
        }
      free(save);
      return(save);
    }
    ensuite dans mon autre fonction2: - je déclare un double pointeur (char **cpy)
    - je fais un cpy = check(i, buffer, col);
    mais apres je ne vois pas comment afficher tous les save [x][y] dans ma fonction2.

    J'ai pensé à une boucle mais je ne vois pas comment faire en sorte que **save devienne un double tableau identique à celui de fonction 1.
    Bref j'espère avoir réussi a vous expliquer mon problème. si vous vous avez des idées je suis preneur, Merci

    ps: pour l'instant j'arrive a affiché le dernier save[x][y] en fesant un return (save[x][y - 1]) mais bon j'ai plein de warning et ca n'affiche qu'un élément de mon tab, pour affiché j'utilise un printf("%c", cpy);

  2. #2
    Expert confirmé
    Inscrit en
    Mars 2005
    Messages
    1 431
    Détails du profil
    Informations forums :
    Inscription : Mars 2005
    Messages : 1 431
    Points : 4 182
    Points
    4 182
    Par défaut
    Les deux dernières lignes de ta fonction sont magnifiques. Consulte la page de manuel de free et éventuellement aussi celle de malloc pour bien comprendre ce que font ces deux fonctions et comment les utiliser.

  3. #3
    Membre chevronné

    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2013
    Messages
    610
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Finance

    Informations forums :
    Inscription : Avril 2013
    Messages : 610
    Points : 1 878
    Points
    1 878
    Billets dans le blog
    21
    Par défaut
    1. Matt a raison, si tu libères la mémoire allouée pour save avant de retourner save, tu ne pourras jamais rien faire de bon avec

    2. Pour ce qui est d'itérer sur un tableau par un pointeur, la difficulté n'est pas très grande. On peut utiliser les crochets [] avec un pointeur également:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    // ptr[2] <=> *(ptr+2)
    // donc
    // ptr[2][3] <=> *(*(ptr+2)+3)
    ce qui est la conduite recherchée si ptr est de type const char **

    Donc la boucle que tu utilises pour un tableau fonctionne.

    Sinon tu boucles en utilisant le pointeur:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    char *p, *ip;
    for (p = save; p < save+save_size; ++p) {
      for (ip = *p; ip < p + col; ++ip) {
        // fais ce que tu as à faire avec *ip
      }
    }
    sachant que si les lignes du tableau save sont des strings terminées par NULL, la boucle intérieure n'est pas forcément nécessaire

  4. #4
    Membre habitué Avatar de awesomeman
    Homme Profil pro
    Étudiant
    Inscrit en
    Octobre 2015
    Messages
    166
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2015
    Messages : 166
    Points : 136
    Points
    136
    Par défaut
    c'est vrai mon free est au mauvais endroit , j'avais pas fais attention
    sinon merci stendhal pour ton premier bout de code avec les tableaux et double pointeur. Par contre pour tes deux boucles je ne vois pas.
    de toute façon, dans tous les cas, je suis obligé de faire un autre tableau dans ma fonction2 pour assigné une par une chaque valeur de save que je viens de return pour les placer dans cpy? (un peu comme dans ma première fonction sauf que mon tableau d'origine est double)

    Enfait à la base je voulais faire ca (pour vérifier que mes données de save sont bien stocké dans cpy):

    cpy = check(i, buffer, col)
    printf("%c", cpy[0][0])

    car c'était le plus simple et le mieux pour mon programme mais c'est surement une erreur puisque le print n'affiche rien ...

  5. #5
    Expert éminent
    Homme Profil pro
    Ingénieur développement matériel électronique
    Inscrit en
    Décembre 2015
    Messages
    1 565
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur développement matériel électronique
    Secteur : High Tech - Électronique et micro-électronique

    Informations forums :
    Inscription : Décembre 2015
    Messages : 1 565
    Points : 7 648
    Points
    7 648
    Par défaut
    Bonjour,

    L'objectif ne me parait pas clair.

    Pour qu'une fonction renvoie à une autre un tableau de lignes, le code est :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    char** renvoie( char ** doubleTableau )
    {
        return doubleTableau ;
    }
    S'il s'agit d'un tableau à deux dimensions, le code est :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    char(* renvoie( char  doubleTableau[][10] ))[10]
    {
        return doubleTableau ;
    }

  6. #6
    Membre habitué Avatar de awesomeman
    Homme Profil pro
    Étudiant
    Inscrit en
    Octobre 2015
    Messages
    166
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2015
    Messages : 166
    Points : 136
    Points
    136
    Par défaut
    En fait , je me suis trompé de problème ,c'est pour ca que ce n'est pas clair du tout. ce n'est pas le return du tableau qui pose problème puisque le tableau n'est pas bon à la base ..
    le problème vient d'une mauvaise affectation des caractère du buffer dans le double tableau, en effet je ne peux pas affiché cpy[3][24] en dehors de ma boucle dans la fonction bsq.
    Par contre lorsque je printf dans la boucle, ca marche ( sauf si mon x est supérieur à 0 ---> cpy[x][y], dans ce cas j'ai un segfault)

    j'ai laissé quelques exemples dans la fonction bsq pour bien comprendre.
    le segfault est peut etre causé par mon x qui est mal mallocé, pour le reste je pense que je n'utilise pas la bonne méthode et que je devrai directement open/read avec un double tableau plutot qu'avec le buffer, mais si il y a une solution pour ne pas trop toucher au code, ca me va
    Merci de votre patience

    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
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    #include <sys/types.h>
    #include <sys/stat.h>
    #include <fcntl.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <unistd.h>
     
    int 	check(int i, char buffer[2000000])// détermine si le bufferde i est égal à o, . ou \n et assigne une valeur 
    {
      if (buffer[i] == 'o')
        return (2);
      else if (buffer[i] == '.')
        return(1);
      else if (buffer[i] == '\n')
        return (0);
    }
    int print(int stock, char **cpy, int x, int y)// affiche et stocke le caractère dans l'emplacement de cpy
    {
      if (stock == 1)
        {
          cpy[x][y] = '.';
          printf("%c", cpy[x][y]);
        }
      if (stock == 2)
        {
          cpy[x][y] = 'o';
          printf("%c", cpy[x][y]);
        }
      if (stock == 0)
        {
          cpy[x][y] = '\n';
          printf("%c", cpy[x][y]);
        }
    }
    char	**bsq(int col, int i, char buffer[2000000], int x)//parcours le buffer[i], malloc et appel les fonction précédentes
    {
      char **cpy;
      int y;
      int stock;
     
      y = 0;
      cpy = malloc(sizeof(char*) * 100);
      while(buffer[i])
        {
          cpy[x] = malloc(sizeof(char) * col);
          stock = check(i, buffer);
          print(stock, cpy, x, y);
          //printf("%c", cpy[0][1]) fonctionne 
          //printf("%c", cpy[2][7]) segfault
          (stock == 1 || stock == 2)?y++:0;
          printf("%c", cpy[x][y - 1]);
          if (stock == 0)
    	{
    	  x++;
    	  y = 0;
    	}
          i++;
        }
      //printf("%c", cpy[0][1])n'affiche rien
      //printf("%c", cpy[47][38]);n'affiche rien 
      free(cpy);
    }
    int read_that(char *filepath, int i)// parcours le fichier pour trouver les nombre de colonnes et de lignes 
    {
      int fd;
      char buffer[2000000];
      int lign;
      int col;
     
      fd = open(filepath, O_RDONLY);
      i = read(fd, buffer, 2000000);
      i = 0;
      lign = 1;
      col = 1;
      while (buffer[i++] != '\n')
        col++;
      i = 0;
      while(buffer[i] != '\0')
        {
          if (buffer[i] == '\n')
    	  lign++;
          i++;
        }
      bsq(col, 0, buffer, 0);
    }
    int	main(int ac, char **av)
    {
      int i;
     
      read_that(av[1], i);
    }

  7. #7
    Expert éminent
    Homme Profil pro
    Ingénieur développement matériel électronique
    Inscrit en
    Décembre 2015
    Messages
    1 565
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur développement matériel électronique
    Secteur : High Tech - Électronique et micro-électronique

    Informations forums :
    Inscription : Décembre 2015
    Messages : 1 565
    Points : 7 648
    Points
    7 648
    Par défaut
    Bonjour,

    Le point obscur vient de ce que représente un char**.
    char** cpy; est un pointeur.
    Un pointeur qui pointe sur un pointeur ou une ligne de pointeurs. Ce qui donne à l'utilisation l'image d'un tableau à 2 dimensions, mais pour cela il faut allouer toutes les lignes.

    cpy = malloc( sizeof(char*) * nb ) alloue une ligne de 'nb' pointeurs
    ces 'nb' pointeurs doivent aussi être alloués pour être utilisables.
    Si on fait :
    cpy[x] = malloc(sizeof(char) * col); un unique pointeur cpy[x] est alloué,
    et cpy[x][n] est une zone de mémoire valide pour tout n compris entre 0 et col-1
    mais cpy[y] est un pointeur jamais alloué, donc cpy[y][n] provoque un accès invalide!

    Dans la fonction bsq(), les deux variables i et x représentent forcément la même chose et doivent avoir la même valeur.

    On peut pré-allouer la table par :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    char **allouer_tableau( int col , int lig )
    {
        char **cpy = malloc( sizeof(char*) * lig );
        for ( int i = 0 ; i < lig ; ++i )
            cpy[i] = malloc( sizeof(char) * col );
        return cpy;
    }
    et attention, quand on n'a plus besoin du tableau de tableau, on doit le désallouer par :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    void liberer_tableau( char** cpy , int lig )
    {
        for ( int i = 0 ; i < lig ; ++i )
            free( cpy[i] );
        free( cpy );
    }

  8. #8
    Membre habitué Avatar de awesomeman
    Homme Profil pro
    Étudiant
    Inscrit en
    Octobre 2015
    Messages
    166
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2015
    Messages : 166
    Points : 136
    Points
    136
    Par défaut
    Merci beaucoup mon problème est résolu, cependant je ne vois pas en quoi il est obligatoire d'allouer la mémoire dans une autre fonction .. pourquoi c'est impossible de le faire dans la fonction qui utilise cet espace ?

  9. #9
    Expert éminent
    Homme Profil pro
    Ingénieur développement matériel électronique
    Inscrit en
    Décembre 2015
    Messages
    1 565
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur développement matériel électronique
    Secteur : High Tech - Électronique et micro-électronique

    Informations forums :
    Inscription : Décembre 2015
    Messages : 1 565
    Points : 7 648
    Points
    7 648
    Par défaut
    Citation Envoyé par awesomeman Voir le message
    Merci beaucoup mon problème est résolu, cependant je ne vois pas en quoi il est obligatoire d'allouer la mémoire dans une autre fonction .. pourquoi c'est impossible de le faire dans la fonction qui utilise cet espace ?
    On aurait tout à fait pu le faire dans la fonction, l'allocation dans une autre c'est juste pour séparer plus clairement les traitements.

  10. #10
    Membre habitué Avatar de awesomeman
    Homme Profil pro
    Étudiant
    Inscrit en
    Octobre 2015
    Messages
    166
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2015
    Messages : 166
    Points : 136
    Points
    136
    Par défaut
    ca marche , merci pour tes réponses et pour ton temps

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

Discussions similaires

  1. Réponses: 2
    Dernier message: 14/02/2011, 15h56
  2. Réponses: 2
    Dernier message: 31/12/2007, 13h50
  3. Utiliser un tableau dans une autre frame
    Par reureu dans le forum VB.NET
    Réponses: 2
    Dernier message: 03/08/2007, 14h23
  4. Réponses: 5
    Dernier message: 29/06/2006, 17h23
  5. Pb pour se servir d'un tableau dans une autre unité
    Par libititi dans le forum Langage
    Réponses: 7
    Dernier message: 08/06/2005, 11h40

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