Référence indéfinie à ' sin ' [dupliquer]
Cette question a déjà une réponse ici:
J'ai le code suivant (réduit aux bases bues pour cette question):
#include<stdio.h>
#include<math.h>
double f1(double x)
{
double res = sin(x);
return 0;
}
/* The main function */
int main(void)
{
return 0;
}
En le compilant avec gcc test.c
j'obtiens l'erreur suivante, et je ne peux pas comprendre pourquoi:
/tmp/ccOF5bis.o: In function `f1':
test2.c:(.text+0x13): undefined reference to `sin'
collect2: ld returned 1 exit status
Cependant, j'ai écrit divers programmes de test qui appellent sin
depuis la fonction main
, et ceux-ci fonctionnent parfaitement. Je dois faire quelque chose de manifestement mal ici - mais quel est-il?
4 réponses
Vous avez compilé votre code avec des références aux mathématiques correctes.h fichier d'en-tête, mais lorsque vous avez tenté de le lier, vous avez oublié l'option d'inclure la bibliothèque mathématique. Comme un résultat, vous pouvez compiler votre .o fichiers objet, mais pas créer votre exécutable.
Comme Paul l'a déjà mentionné, ajoutez "-lm
" pour créer un lien avec la bibliothèque mathématique à l'étape où vous essayez de générer votre exécutable.
Dans le commentaire, linuxD demande:
Pourquoi pour
sin()
dans<math.h>
, avons-nous besoin de-lm
option explicitement; mais, pas pourprintf()
dans<stdio.h>
?
Parce que ces deux fonctions sont implémentées dans le cadre de la "spécification UNIX unique". Cette histoire de cette norme est intéressante et est connue sous de nombreux noms (IEEE Std 1003.1, X / Open Portability Guide, POSIX, Spec 1170).
Cette norme, sépare spécifiquement les routines" bibliothèque C Standard "des routines" bibliothèque mathématique C Standard " (page 277). Le passage pertinent est copié ci-dessous:
Bibliothèque C Standard
La bibliothèque C Standard est automatiquement recherchée par
cc
pour résoudre les références externes. Cette bibliothèque prend en charge tous les interfaces du système de Base, telles que définies dans le Volume 1, à l'exception Routines Mathématiques.Bibliothèque Mathématique Standard C
Cette bibliothèque prend en charge les routines mathématiques du système de Base, telles que définies dans le Volume 1. L'option
cc
-lm
est utilisé pour rechercher cette bibliothèque.
Le raisonnement derrière cette séparation a été influencé par un certain nombre de facteurs:
- les guerres UNIX ont conduit à une divergence croissante par rapport à L'offre originale D'AT&T UNIX.
- le nombre de plates-formes UNIX a ajouté des difficultés dans le développement de logiciels pour le système d'exploitation.
- une tentative de définir le plus petit dénominateur commun pour les développeurs de logiciels a été lancée, appelé 1988 POSIX .
- les développeurs de logiciels programmés par rapport à la norme POSIX pour fournir leurs logiciels sur des "systèmes compatibles POSIX" afin d'atteindre plus de plates-formes.
- les clients UNIX ont exigé des systèmes UNIX "compatibles POSIX" pour exécuter le logiciel.
Les pressions qui ont alimenté la décision de mettre -lm
dans une bibliothèque différente probablement inclus, mais ne sont pas limités à:
- cela semble être un bon moyen de réduire la taille de la libc, autant d'applications n'utilisez pas de fonctions intégrées dans la bibliothèque mathématique.
- Il offre une flexibilité dans l'implémentation des bibliothèques mathématiques, où certaines bibliothèques mathématiques s'appuient sur des tables de recherche intégrées plus grandes tandis que d'autres peuvent s'appuyer sur des tables de recherche plus petites (solutions informatiques).
- pour les applications vraiment contraintes de taille, il permet des réimplémentations de la bibliothèque mathématique d'une manière non standard (comme sortir juste
sin()
et le mettre dans une bibliothèque personnalisée.
En tout cas, il fait maintenant partie de la norme ne doit pas être automatiquement incluse dans le langage C, et c'est pourquoi vous devez ajouter -lm
.
J'ai le problème de toute façon avec-LM ajouté
gcc -Wall -lm mtest.c -o mtest.o
mtest.c: In function 'f1':
mtest.c:6:12: warning: unused variable 'res' [-Wunused-variable]
/tmp/cc925Nmf.o: In function `f1':
mtest.c:(.text+0x19): undefined reference to `sin'
collect2: ld returned 1 exit status
J'ai découvert récemment que cela ne fonctionne pas si vous spécifiez d'abord-lm. L'ordre compte:
gcc mtest.c -o mtest.o -lm
Juste lien sans problèmes
Vous devez donc spécifier les bibliothèques après.
Vous devez lier avec la bibliothèque mathématique, libm:
$ gcc -Wall foo.c -o foo -lm
J'ai eu le même problème, qui est parti après avoir listé Ma bibliothèque en dernier: gcc prog.c-lm