Tableau Dynamique dans une fonction

Fermé
Durius - 14 févr. 2009 à 14:21
fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 - 14 févr. 2009 à 21:41
Bonjour,

J'ai un petit probleme avec mon tableau dynamique.
J'ai un tableau rempli que je met en parametre d'entrée dans une fonction. Cette fonction doit supprimer le tableau mis en entrée et recuperer des variables avec des scanf/getch et les mettre dans differentes case du tableau de la fonction. ce tableau doit avoir une taille qui s'augmente tans que l'utilisateur veut qu'il s'augmente.
Mon probleme c'est que le tableau de la fonction n'est pas recopié dans le tableau mis en parametre d'entrée. Pourtant on sait qu'un tableau s'utilise en entrée/sortie. Mais un pointeur?
C'est la premiere fois que j'utilise les pointeurs pour faire des tableau dynamique (ma fonction marche trés bien en tableau statique).
Voici mon code

Pardon il es en .txt car jai pas visual studio sur ce pc.

#include "Tout.h"

Pop est declaré dans le main en tans que pointeur de type TP.

main :

iNbGens =0;

/* Appel :*/ Init(Pop, iNbGens);


//Fonction :

void Init(TP* P, int &iDim)
{
int iCompt=-1;

do
{
iDim ++;
P = (TP*) malloc(iDim * sizeof(TP));

iCompt++;

printf("Age?\n" );
scanf("%d",& P[iCompt-1].Age);


printf("Nouveau ?\n\t\tO pour Oui\t N pour Non\n" );
iNew =_getch();
}while((iNew !='n')&&(iNew!='N'));
}

Dim est mis a 0 au debut de la fonction par son appel avec iNbGens = 0; et a la fin renvoi la bonne valeur.
Mais aprés quand je fai un printf du tableu mis en entrée de la fonction celui ci na pas ete modifié.
Merci de me repondre le plus vite possible.
A voir également:

13 réponses

fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 1 844
14 févr. 2009 à 15:08
Salut,
Déjà, si tu fais du C++ utilise plutôt l'opérateur new que malloc ;)
Et si tu utilises du C, n'utilise pas le passage par référence. Au choix lol.

Sinon, pour ton tableau, c'est normal que ça ne s'alloue pas dans la fonction étant donné que tu passes la copie de l'adresse du tableau. Il faut envoyer un pointeur sur cette adresse.
Donc le prototype de la fonction devient :
void Init(TP** P, int *iDim) 

L'allocation dans la fonction sera :
*P= malloc(*iDim * sizeof(TP)); 

Pas obliger de caster ;). Par contre n'oublie pas de tester la valeur de retour de malloc. Si le pointeur est NULL, ça risque de segaulter par la suite. De plus, si tu veux allouer à la vollé une case de plus à chaque itération (pas très efficace mais bon), utilise plutôt realloc. Cela évitera que tu perdes les valeurs de ton tableau ;)
Et l'appel de la fonction Init dans le main() deviendra :
Init(&Pop, &iNbGens); 


Et enfin n'oublie pas de faire un free() à la fin ;).
Cdlt
2
Merci beaucoup, je vais essayé pour voir ;). Et je vous tiens au courant.
0
re donc je rappellle que Pop est declaré par

TP* Pop;

Ce qui m'entraine une erreur de compile sur

void Init(TP** P, int *iDim)

en me disant que c'est impossible de de convertir TP* et TP**.

Comment faudrai que je fasse ?

Et Ensuite il me crache plein d'erreur en me disant que la partie de gauche de .Age doit avoir un class/struct/union, le type est TP*, souhaitez-vous utilier '->' à la place?

j'ai essayé des petits trucs mais rien n'y fait.
0
fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 1 844
14 févr. 2009 à 16:33
Quelle est la définition de TP ?
Sinon oui tu peux utiliser la notation fléchée. L'essentiel est d'utiliser *P et comme, P->blabla équivaut à (*P).blabla, pas de soucis ;)
Cdlt
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
Tp est un typedef struct avec comme variable l'Age, etc..
0
La j'ai mis Pop en TP**Pop, cela a supprimé la premiere erreur, et j'ai mis biens des parenthese pour (*p).Age et la ça me suprime mes erreur. je vais corriger tout mes autres fonctions. car j'utilisai Pop en TP* Pop au lieu de TP** Pop.

Je vous tiens au courant du resultat
0
fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 1 844
14 févr. 2009 à 16:56
Normalement t'as pas besoin de mettre Pop en TP** du moment que tu envoies &Pop vu que tu envoies le pointeur sur une adresse, ce qui fait déjà TP** dans le corps de la fonction appelée. Mais bon tu peux aussi déclarer Pop en TP** et envoyer Pop tout court.
Cdlt
0
Donc j'ai fai comme tu ma dis, j'ai repassé Pop en TP*. j'ai corrigé toutes les erreurs. Mais il y a plantage du programme.
J'ai une fonctione en debut de programme qui recupere des variables dans un fichier .txt donc qui ecrit dans Pop.
Quand je test mon programme ça me met :

Exeception non gérée à 0x67cc6af2 dans Programme.exe : 0xC0000005: Violation d'accés lors de l'écriture à l'emplacement 0xcccccccc.

C'est le pointeur qui ecrit dans l'allocation de memoire de windows ou un truc comme ça non?

Et comment puis-je faire pour remedier a ce plantage?
0
fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 1 844
14 févr. 2009 à 17:50
Salut,
Poste ton programme ici que je vois dans l'ensemble. Et n'oublie pas de me donner la déclaration de TP.
0
Re,

Voici la fonction qui fait planter mon programme avec l'erreur que jai cité au dessu.


//dans le .h
typedef struct
{
int iAge;
}TP;



//Main.cpp

Pop= (TP*) malloc(*iNbre * sizeof(TP));//iNbre est recupéré avec une fonction lisant le .txt mais cette fonction donnant iNbre Marche trés bien.


Demarrage(&Pop, iNbre);

//fonction


void Recup(TPapier** p, int iDim)//fonction de lecture remplissant le tableau Pop qui est dans le main
{
int iBcl2;
int iBcl5;
FILE*fd;
fd=fopen("Data.txt","r");


for(iBcl2=0; iBcl2<iDim; iBcl2++)
{
iBcl5=iBcl2+1;
fscanf(fd,"\n\t\tNombre %i\n",&iBcl5);
fscanf(fd,"Age : %d", &(*p[iBcl2]).iAge); //ici plante le programme
}
fclose(fd);
0
fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 1 844
14 févr. 2009 à 20:48
Là tu parles de TPapier, je suis plus ^^.
Sinon je t'ai dit que tu avais besoin d'un double pointeur lorsque tu voulais allouer la zone mémoire. Donc dans ta fonction Recup, tu n'as pas besoin de faire passer un double pointeur. Un simple pointeur suffira largement ;)
0
plantage au deuxieme passage dans la boucle for
0
fiddy Messages postés 11069 Date d'inscription samedi 5 mai 2007 Statut Contributeur Dernière intervention 23 avril 2022 1 844
14 févr. 2009 à 21:41
C'est pas évident de t'aider. Je sais même pas à quoi ressemble ton fichier de données Data.txt.
Par contre, quand tu as utilisé le double pointeur, je vois une erreur à ce niveau.
fscanf(fd,"Age : %d", &(*p[iBcl2]).iAge);

Il faut mettre *p entre parenthèse. Ce qui donne :
fscanf(fd,"Age : %d", &(*p)[iBcl2]).iAge;

Mais si tu utilises un pointeur simple juste p suffira.
A chaque fois que tu fais un changement, dis ce que tu as mis. Ca sera plus facile pour aider.
Sinon une autre piste pour mets une simple variable int pour récupérer l'âge.
Et affiche l'âge avec un printf, tu verras si l'erreur vient de là ou pas.
0