我目前正在尝试编译一些从未出现任何问题的旧代码 - 直到现在我再次在Ubuntu中使用它。(gcc 4.8.2)
问题是由#define中的随机数生成器引起的,该文件看起来基本上是这样的:
**Lights.h:**
#if defined(__linux) || defined(__linux__)
unsigned int seed = time(NULL);
#define RND ((double)rand_r(&seed)/RAND_MAX) // reentrant uniform rnd
#endif
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__)
#define RND ((double)rand()/RAND_MAX) // uniform rnd
#endif
class Lights {
.... //various structs and functions, using RND
}
**Lights.cpp**
#include Lights.h
....
//implementation of functions, also using RND

这总是没有问题,但现在我在编译时遇到以下错误:
CMakeFiles/luxrender.dir/qtgui/lightSourceCleaner.o: In function `qt_noop()':
/home/.../Lights.cpp:131: multiple definition of `seed'
CMakeFiles/.../mainwindow.o:/home/.../mainwindow.cpp:103: first defined here
CMakeFiles/...mainwindow.o: In function `MainWindow::startLsc()':
mainwindow.cpp:(.text+0x167b4): undefined reference to `Lights::cleanLightGroups(QProgressDialog&, int, int, int, double, double, double, bool, bool, double, double)'
collect2: error: ld returned 1 exit status
make[2]: *** [luxrender] Error 1
make[1]: *** [CMakeFiles/luxrender.dir/all] Error 2

所以我在这里有点困惑,因为没有重新定义种子"实际上,在mainwindow.cpp中,第103行涉及一个我从未在此上下文中使用过的函数(它与日志记录有关。)
我不知道qt_noop()是什么(可能是与QT GUI相关的smtgh,但在这种情况下我从不接触过这个)。
"种子"不是任何其他定义的,只有Lights.h有这个#define,而Lights.h只包含在mainwindow.cpp中。
任何想法可能是什么问题? (正如我所说,这有效,但是2年前 - gcc 4.8.2最终有什么变化?)
答案 0 :(得分:0)
它在标题中定义,意味着每个翻译单元中都会有一个包含标题的定义;因此,您可以从多个位置包含多个定义:Lights.cpp
和mainwindow.cpp
。相反,只需在标题中声明它:
extern unsigned int seed;
并在一个源文件中定义它:
unsigned int seed = time(NULL);
然后再考虑一下你是否想要一个全局变量,以及是否要将不可靠的rand
函数与不可靠的种子一起使用。