turnerom
Messages postés492Date d'inscriptionsamedi 10 juillet 2004StatutMembreDernière intervention12 janvier 2012
-
9 mai 2006 à 12:01
cs_AlexN
Messages postés694Date d'inscriptionlundi 5 décembre 2005StatutMembreDernière intervention 8 janvier 2014
-
11 mai 2006 à 15:59
Bonjour,
je n'arrive pas à compiler ce petit programme servant a illustrer mon problème :
return 0;
}
<hr size="2" width="100%">
Ce programme ne fait pas grand chose, il sert juste d'illustration au problème que je rencontre.
Pourquoi le compilo me dit-il : fichier.cpp:40: error: argument of type `void*(Foo::)(void*)' does not match `void*(*)(void*)'
Et comment résoudre mon problème.
D'avance merci !
cs_AlexN
Messages postés694Date d'inscriptionlundi 5 décembre 2005StatutMembreDernière intervention 8 janvier 201419 9 mai 2006 à 16:20
Il s'agit d'un problème de transtypage, mais je ne vois pas trop non plus. pcreate_thread ne semble pas aimer les parametres de type fonction membre ou le transtypage n'est pas écrit correctement.
Il doit y avoir un moyen de forcer mais je ne vois pas. désolé.
essayes ça : c'est pas la bonne solution mais ça compile semble-t-il
void * p (void *t) {
((Foo *)t)->affiche(t);
}
int main()
{
pthread_mutex_init (&mutex, NULL);
pthread_t thrd1;
Foo f;
pthread_create(&thrd1,NULL,p,(void *)&f);
pthread_join(thrd1, NULL);
cout << "Fin" << endl;
return 0;
}
Par contre si quelqu'un comprend son problème je suis aussi preneur !
olbal
Messages postés20Date d'inscriptionvendredi 16 mai 2003StatutMembreDernière intervention29 septembre 2006 10 mai 2006 à 13:19
[auteurdetail.aspx?ID= 638418 AlexN]-> structure et classe c'est la même chose comme l'a expliqué [auteurdetail.aspx?ID=304809 turnerom] mis à part la valeur par défaut d'accès qui est dans un cas est public et dans l'autre est privé; et une fonction membre ayant pour nom le nom de la structure, est bien un constructeur de la stucture, de même que la structure peut avoir un destructeur, etc...
[auteurdetail.aspx?ID=304809 turnerom]: Concernant l'erreur, elle vient du fait que tu passes l'adresse d'une fonction membre de structure Foo `void*(Foo::)(void*)' alors que la fonction pthread_create attend l'adresse d'un fonction simple `void*(*)(void*)'. En simplifiant pour le compilateur, l'appel d'une fonction membre se fait comme l'appel d'une fonction simple mais avec en plus la transmission d'un paramètre supplémentaire (et caché) qui est le pointeur sur la (structure ou la classe): C'est le fameux 'this'. C'est comme cela que se fait le lien entre les fonctions membre de l'objet et les données de l'objet. Il me semble d'ailleurs que les 1er compilateurs C++ ne permettait pas d'obtenir l'adresse d'une fonction membre, ce qui n'était pas plus mal car l'adresse d'une fonction membre sans l'adresse de l'instance de la classe à laquelle elle appartient n'est pas utilisable sauf en assembleur puisque la on peut rajouter le pointeur (this) sur la pile.
La solution d'[auteurdetail.aspx?ID =638418 AlexN] est donc exacte.On aurait pu parvenir au même résultat, en rendant la fonctions affiche static et la le paramètre void *p_data avait une utilité
turnerom
Messages postés492Date d'inscriptionsamedi 10 juillet 2004StatutMembreDernière intervention12 janvier 20121 9 mai 2006 à 12:29
Non, ca ne vient pas de la.
Dans mon prog j'ai bien class et j'ai la meme erreur.
De plus une structure n'est jamais qu'une classe ou tout les membres sont publics.
cs_AlexN
Messages postés694Date d'inscriptionlundi 5 décembre 2005StatutMembreDernière intervention 8 janvier 201419 9 mai 2006 à 12:50
Hum si les structures c'etaient stricto senso la même chose qu'une classe, personne les aurais inventé.
Ok syntaxiquement ça se ressemble. Mais les traitements et les propriétés d'une structure et d'une classe sont très très différents...Entre autres, ta fonction Foo() pour la structure est juste une fonction, tandis que pour la classe Foo c'est un constructeur.
En ce qui concerne les structure auto reférentes, il faut toujours faire préceder la définition de la structure par une declaration du type pointeur sur struct. Tu ne peux pas declarer la classe Foo, avant de l'avoir défini. Le compilateur ne connait pas la taille avant la definition. Il ne connait que la taille d'un pointeur.
return 0;
}
<hr size="2" width="100%">
Pourquoi le compilo me dit-il : fichier.cpp:40: error: argument of type `void*(Foo::)(void*)' does not match `void*(*)(void*)'
Et comment résoudre mon problème.
D'avance merci !
cs_AlexN
Messages postés694Date d'inscriptionlundi 5 décembre 2005StatutMembreDernière intervention 8 janvier 201419 9 mai 2006 à 14:45
Ligne 40 c'est laquelle ?
vient du parametre de pthread_create() ? Le compilateur semble te dire qu'il attend un paramatère de type void*(*)(void*).
tentes un cast void*(*)(void*) sur le paramètre f.affiche()
cs_AlexN
Messages postés694Date d'inscriptionlundi 5 décembre 2005StatutMembreDernière intervention 8 janvier 201419 10 mai 2006 à 13:53
Juste un truc,
Je ne penses pas qu'une structure puisse être dérivée, ni que ses fonction membres puisse être surchargées ou virtualisées. Ni même que tous les mécanismes liés aux classes/objets (en dehors de la construction et destruction) pouvaient être applicables aux structures. Et j'ai quand même un doute.
Notemment je cite : Bjarne Stroustrup "Le langage C++" - Chapitre 5 - Les classes - 5.2.1-5.2.2 :
struct date {
int month, date, year;
void set (int, int, int);
void get (int *, int *, int *);
void next();
void print();
}
"La déclaration de date dans le paragraphe précédent offre un ensemble de fonctions pour la manipuler, mais elle ne précise pas que ces fonctions peuvent être les seules à pouvoir accéder aux objets de type date. Cette restriction peut être exprimée en utilisant une classe au lieu d'une struct : "
class date {
int month, date, year;
public:
void set (int, int, int);
void get (int *, int *, int *);
void next();
void print();
}
Le fait de distinguer struct et class par deux mots reservés implique que les mécanismes mis en jeu ne sont pas identiques. Sinon c'est de la redondance.
turnerom
Messages postés492Date d'inscriptionsamedi 10 juillet 2004StatutMembreDernière intervention12 janvier 20121 10 mai 2006 à 14:13
La différence se situ dans le fait que dans une struct tout est public et tu ne peux rien mettre en "private" ni "protected".
Alors que dans unje class par défaut tout est privé mais tu peux mettre des choses "public".
Or c'est bien ce qui est dit. Dans
class date {
int month, date, year;
public:
void set (int, int, int);
void get (int *, int *, int *);
void next();
void print();
}
month, date et year étant privé (par défaut) seule des fonctions membres de date pouront y avoir accès comme ici set, get, ....
Alors qu'avec la structure tu peux faire un:
date d;
d.month=11;
Alors qu'avec la class tu te feras jeté, il faudra que tu utilise le "setter" :
date d;
d.set(1,11,2006);
Je pensais que class = struct sans exception, en fait j'ai appris sur cette page qu'il y en avait une si on utilise template.
[auteurdetail.aspx?ID=304809 turnerom]-> Dans une structure les membres sont par défaut public mais rien empêche d'utiliser private ou protected. C'est en C pur que tout les membres sont forcément public mais dans ce cas en ne peut avoir que des membres de type variable, car le concept de fonction membre n'existe pas.
[auteurdetail.aspx?ID =638418 AlexN] -> Tu as écrit :"Le fait de distinguer struct et class par deux mots reservés implique
que les mécanismes mis en jeu ne sont pas identiques. Sinon c'est de la
redondance."
if et goto suffisent pour faire n'importe quel type de boucle pourtant for, while, do...while existent!