我正在尝试编译两个.cpp文件,(foo.cpp和bar.cpp)并构建一个共享对象(project.so)。但是编译失败了(我的错误的一部分)是:
....
duplicate symbol _n in:
foo.o
bar.o
ld: 5 duplicate symbols for architecture x86_64
clang: error: linker command failed with exit code 1(use -v to see
invocation)
make: *** [project.so] Error 1
ERROR: compilation failed for package ‘project’
我的.cpp文件有几个常见和不常见的头文件,一些常见和不常见的命名函数,以及一组通常命名的变量:
Foo.cpp中
#include <iostream>
#include <fstream>
#include <vector>
#include <ctime>
#include <cmath>
size_t m1;
double k1=2.0;
std::vector<double> x,y;
std::vector<double> z;
size_t n,p;
void inputfoo(){...}
void output(){...}
bar.cpp
#include <iostream>
#include <fstream>
#include <vector>
#include <ctime>
#include <cmath>
#include "Eigen/Dense"
#include "Eigen/Cholesky"
size_t m2;
double k2=2.0;
std::vector<double> x,y;
std::vector<double> z;
size_t n,p;
void inputbar(){...}
void output(){...}
我的尝试:
如果我在每个.cpp文件中区分全局变量的名称,我可以获得较少数量的“重复符号”错误。也就是说,如果我将bar.cpp中的size_t m
更改为foo.cpp中的size_t m1
和size_t m2
,我就不会将此部分更改为错误
duplicate symbol _m in:
foo.o
bar.o
所以,现在我可以看到错误中的5个符号是针对x,y,z,n,p(在每个.cpp文件中全局定义的)
如果我将通常命名的函数的名称不同,那么同样如此。以前,我也会在错误中得到这一部分,
duplicate symbol __Z4inputP4init3RNGPi in:
foo.o
bar.o
将我引导到input(){...}函数。
因此,我将一个通常命名的函数(input(){..})的名称更改为inputfoo
和inputbar
,并且相应的错误消失了。
现在,我确信如果我在每个文件中使名称唯一,我将能够成功编译这两个。但是,我无法更改x,y,z,n,p,因为它们在这些文件中很多,我有更多的文件可以使用,它们具有共同的命名函数和变量。
任何人都可以向我解释一下这里发生了什么以及如何解决这个问题?我真的很想知道造成这种情况的原因。我尝试阅读以前的帖子“Understanding the origin of a linker duplicate symbol error”,但我不认为这是与标题相关的问题。
非常感谢你。
答案 0 :(得分:5)
示例不完整,这使评论很难。
但是让我猜一下:你在两个文件中都有全局,并且两者都可见。这是一个设计错误。你可以
static
作为extern
来共享它们。但您引用的错误有所不同,我们对您的input::init()
...
另外,我在这里也看不到任何与Rcpp有关的内容,那么为它添加标签吗?