Citation :
les template vont dans les .h point
|
Pas terrible, ce genre de réponse.
Les templates vont dans les .h, pourquoi ? Qu'est-ce qu'un fichier .h a de particulier, sachant que le précompilateur se contente de copier bêtement les include comme des sacs de caractères ? Est-ce que ça marche encore si je donne à mon header une extension .hpp, ou -soyons fous- .cpp ?
Se contenter d'apprendre bêtement que les templates vont dans les .h, c'est passer à côté de la raison simple et logique qui fait que les choses sont ainsi.
Si les templates vont dans les .h, c'est simplement parce que les templates sont des morceaux de code que le compilateur va spécialiser en attribuant des valeurs aux paramètres de template selon les besoins, en inspectant le code qui les utilise. Sachant que le résultat de la compilation du code templaté dépend des paramètres de template, qui peuvent prendre une infinité de valeur (par exemple des classes pas encore écrites), il est impossible de compiler le code templaté d'un côté, puis de le linker ensuite. Il faut pouvoir générer le binaire à la demande, et donc avoir accès non pas seulement aux prototypes, mais aussi à l'implémentation. Sachant qu'en général les gens n'#includent pas l'implémentation mais seulement les headers, il faut mettre l'implémentation dans les headers pour que le compilateur ait toutes les infos nécessaires au moment de la compilation.
Donc pour résumer, sue soeur debeat, voilà ce que le compilateur essaie de faire quand tu veux compiler ton bout de code :
- il voit que tu utilises un template, il prend les paramètres de template que tu utilises (ou qu'il arrive à deviner), et il génère un bout de code "détemplaté" par substitution des paramètres. En l'occurence, la seule chose qu'il détemplate est ton prototype de fonction, car c'est la seule chose qui a été incluse par le préprocesseur. Là par exemple, il a généré deux prototypes, en effectuant les substitutions T=int, et T=unsigned int
- comme il n'a trouvé que des prototypes dans le code à compiler, il les utilise en espérant que le linker saura se débrouiller avec
- étant donné que rien n'utilise ton template dans global.cpp, il n'a probablement rien compilé et donc :
- Quand le linker essaie de trouver les symboles correspondant à tes appels de fonction, il n'en trouve aucun et laisse tomber.
Bon, j'espère que je ne suis pas trop loin de la vérité, je ne suis pas un expert C++, loin de là, mais quand je vois des règles du genre "les templates vont dans les .h" j'essaie de comprendre pourquoi, et je trouve les raisons d'être de ces règles bien plus instructives que les règles elles-mêmes, qui sinon semblent un peu sorties de nulle part et ne sont utiles que dans des cas bien particuliers.
---------------
Any sufficiently complex bug is indistinguishable from magic.