我有一个叫做sin,cos和acos的ac程序。 当我编译时,我得到以下错误:
/tmp/ccDfW98S.o: In function `zip_search': main.c:(.text+0xf30): undefined reference to `sin' main.c:(.text+0xf45): undefined reference to `sin' main.c:(.text+0xf66): undefined reference to `cos' main.c:(.text+0xf7b): undefined reference to `cos' main.c:(.text+0xf9c): undefined reference to `cos' main.c:(.text+0xfc6): undefined reference to `acos' collect2: ld returned 1 exit status
我知道这是常见的,当你不使用-lm gcc标志。 我使用这个标志。 我打电话给这样的GCC:
gcc -o zipcode-server -lm main.c
当我在我的一台电脑上编译,这工作正常。 唯一的区别是我能想到的是,这不是在x86_64上工作,它的工作电脑是i686。 两者都是Ubuntu。 libm.a文件存在于计算机上,它不工作,我没有得到任何错误,说它找不到。 什么可能导致这个?
你应该在main.c
之后加上-lm
一般来说,如果你有多个库,他们应该按照他们的使用顺序编写。 例如,如果库A
使用库B
,则应该有-lA -lB
。
在你的情况下,作为main.c
使用库m
的编译结果的目标文件,因此-lm
应该在它之后。
好奇的是,这主要是出于效率的原因。 通过这个方案,链接器可以用参数列表中的每个新库来解析当前未知的符号,并在途中从该库中拾取新的未知符号。 这意味着链接器可以逐个访问这些库,从而将未知的符号与每个库提供的少量符号进行匹配。
相反,链接器可以一次加载来自所有库的符号,然后开始匹配未知符号。 然而,在这种情况下,链接器需要处理更多的符号,增加了链接器的内存占用量和执行时间。
由于这些库总是可以按照它们的依赖关系1的顺序被声明给链接器,链接器没有理由选择低效率的方式。
1 图书馆通常有一个单向的关系,就是说一个人使用另一个。 图书馆之间的循环依赖关系是很少见的,但是仍然可以通过重复检查某些图书馆来使用这个模型。