奇怪的“多个定义"类型错误 [英] Strange type of "multiple definition of" error

查看:220
本文介绍了奇怪的“多个定义"类型错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用Qt/MinGW/Windows进行大型项目.最近,我更改了一些源文件的位置并重新编译它们,经过更正后,我开始收到诸如

I'm working in a big project with Qt/MinGW/Windows. Recently I changed the places of some of my source files and recompile them, and after some corrections, I began to receive messages such as

(.idata$5+0x0):-1: error: multiple definition of `_imp___ZN9QwtThermo16staticMetaObjectE'

这种情况发生在两个类上:QwtThermo和QwtPlotPicker在以前没有这种错误的代码中(请记住:我只是将基本文件夹中文件的位置更改为某些子文件夹;没有代码更改(据我所记得),请注意,还包括许多其他Qwt类,它们通常可以正常使用而不会产生任何编译错误;这是唯一两个给我带来麻烦的类.

This happens regarding two classes: QwtThermo and QwtPlotPicker in a code where previously there was no such error (remember: I just changed the places of the files in the base folder to some subfolders; no code changed (as far as I remember) and notice that many other Qwt classes are also included and normally used without any compile error; this are the only two ones that are giving me problems).

现在多重定义"是C ++中的一个常见错误,我已经知道通常如何解决它(很多线程,包括StackOverflow,都在谈论它):一个人应该只在头文件中声明内容,而在其中定义它们.cpp文件.

Now "multiple definition of" is a common error in C++ and I already know how one would normally solve it (many threads, including in StackOverflow, talk about it): one should only declare things in header files while defining them in the .cpp files.

不幸的是,这一次似乎不是可行的解决方案.这是怎么回事:

Unfortunately this doesn't seem to be a viable solution this time. Here is what is going on:

  • 我对包含此标头的位置进行了研究,但没有发现任何问题.令我难过的是,它以前曾经很好地编译过.
  • 仅当我创建QwtPlotPicker的子类时,该问题才会出现(与使用QwtPlotPicker无关).如果仅在标头中声明子类的名称并在.cpp中定义它,那么我就可以进行编译,但是一旦我开始使用它(在标头中声明了成员指针),便可以进行编译出现错误'vtable for Picker'的未定义引用".因此,在标头中声明该类并在.cpp中定义它实际上并没有帮助;
  • 使用QwtThermo,如果我将文件包含在头文件中,并且仅声明指向该文件的指针(无子类),则该错误已经开始出现.如果仅在项目的标头中声明QwtThermo类,并在.cpp文件中包含QwtThermo自己的标头,则可以解决此问题.这样,我就可以声明一个指向它的成员指针,并在其父类内的.cpp文件中用"new"实例化该指针,但是一旦我通过调用其方法开始使用它,即""开始再次出现.

因此,正如您所看到的,这似乎不只是在标头中声明并在.cpp中定义它"的问题;还有更多的事情发生. :T

So as you may see, it would seem that this time it's not just a matter of "declare in the header and define it in the .cpp"; something more is going on. :T

那怎么可能出问题了?抱歉,没有发布任何代码,但是请相信我,已经可以看到的所有有趣的东西都已经编写了;张贴代码的唯一更改是通过复制超过5000行^^

So what could be wrong? Sorry not posting any code, but believe me that everything of interesting of it that could be seen was written already; the only change of posting the code would be by copying more then 5000 lines ^^

很高兴您能给我提供任何帮助:)

I'm glad for any help you can give me :)

谢谢

EDIT :这是Qt Creator的编译输出"中的代码:

EDIT: Here is the code from Qt Creator's "Compile Output":

g++ -c -pipe -fno-keep-inline-dllexport -g -frtti -Wall -Wextra -fexceptions -mthreads -DUNICODE -DMGENERALDEFINES_GUI -DMGENERALDEFINES_DEBUG -DMGENERALDEFINES_GENERAL -DQWT_INCLUDED -DDEBUG -DRELEASE -DQT_NO_DEBUG -DQT_NO_DEBUG_OUTPUT -DQT_PRINTSUPPORT_LIB -DQT_MULTIMEDIA_LIB -DQT_WIDGETS_LIB -DQT_SQL_LIB -DQT_NETWORK_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DQT_NEEDS_QMAIN -I. -I"MSHARE_REPO" -I"MSHARE_COMMON" -I"C:\Qt\Qwt-6.1.0\include" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtPrintSupport" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtMultimedia" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtWidgets" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtSql" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtNetwork" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtGui" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\include\QtCore" -I"build\moc" -I"build\ui" -I"C:\Qt\Qt5.2.1\5.2.1\mingw48_32\mkspecs\win32-g++" -o build\obj\moc_mainwindow.o build\moc\moc_mainwindow.cpp
g++ -Wl,-subsystem,windows -mthreads -o debug\mShare.exe object_script.mShare.Debug  -lglu32 -lopengl32 -lgdi32 -luser32 -lmingw32 -lqtmaind "D:/Minhas obras/Softwares/mShare Project/mShare/SMTPEmail.dll" -lpsapi C:/Qt/Qwt-6.1.0/lib/qwtd.dll "D:/Minhas obras/Softwares/mShare Project/mShare/../../Classes/mLogger/build/debug/mLogger.dll" "D:/Minhas obras/Softwares/mShare Project/mShare/../mShareLib/build/debug/mShareLib.dll" C:/Qt/Qwt-6.1.0/lib/qwt.dll "D:/Minhas obras/Softwares/mShare Project/mShare/../../Classes/mLogger/build/release/mLogger.dll" "D:/Minhas obras/Softwares/mShare Project/mShare/../mShareLib/build/release/mShareLib.dll" -LC:\Qt\Qt5.2.1\5.2.1\mingw48_32\lib -lQt5PrintSupportd -lQt5Multimediad -lQt5Widgetsd -lQt5Sqld -lQt5Networkd -lQt5Guid -lQt5Cored .\build\obj\icone_res.o 
d000171.o:(.idata$5+0x0): multiple definition of `_imp___ZN13QwtPlotPicker16staticMetaObjectE'
d000022.o:(.idata$5+0x0): first defined here
d000171.o:(.idata$6+0x0): multiple definition of `_nm___ZN13QwtPlotPicker16staticMetaObjectE'
d000022.o:(.idata$6+0x0): first defined here
d000172.o:(.idata$5+0x0): multiple definition of `_imp___ZN9QwtThermo16staticMetaObjectE'
d000102.o:(.idata$5+0x0): first defined here
d000172.o:(.idata$6+0x0): multiple definition of `_nm___ZN9QwtThermo16staticMetaObjectE'
Makefile.Debug:246: recipe for target 'debug\mShare.exe' failed
d000102.o:(.idata$6+0x0): first defined here
collect2.exe: error: ld returned 1 exit status
mingw32-make[1]: [debug\mShare.exe] Error 1 (ignored)

推荐答案

好吧,经过一番尝试后,我设法找到了问题所在,但没有完全解决问题的方法.存在该问题的原因是,在Qt .pro文件中,我尝试配置一些特定的配置用于调试编译,而另一些配置用于发布编译,但是由于某些原因,系统未在这两种配置之间进行区分.更具体地说,以下代码应该可以工作:

Well, after some try-and-retry I managed to find WHERE the problem lies - but not how exactly to SOLVE it. The problem exists because in my Qt .pro file I tried to configure some specific configurations for debug compilation and others for release compilation, but for some reason the system is not making distinction between those two configurations. To be more specific, the following code should work:

win32 {
    LIBS += -lpsapi

    debug {
        LIBS += C:/Qt/Qwt-6.1.0/lib/qwtd.dll \
            $${MLOGGER}/build/debug/mLogger.dll \      
            $${MSHARE_LIB}/build/debug/mShareLib.dll  
        DEFINES += DEBUG
    }

    release {
        LIBS += C:/Qt/Qwt-6.1.0/lib/qwt.dll \
            $${MLOGGER}/build/release/mLogger.dll \
            $${MSHARE_LIB}/build/release/mShareLib.dll
        DEFINES += RELEASE \
           QT_NO_DEBUG \
           QT_NO_DEBUG_OUTPUT
    }
} # win32

由于在Qt Assistant文件中有关于qmake的信息,因此是使用辅助作用域编写此类配置的方法:

since in the Qt Assistant files regarding qmake, such is the way to write such configurations with a secondary scope:

win32 {
    debug {
        CONFIG += console
    }
}

我注意到,在评论发布"部分后,问题消失了,并且我能够毫无错误地进行编译;如果删除了注释,则问题返回.同时,尽管我没有注释,但尽管我处于调试编译状态",但我仍然能够注意到版本定义已定义.最后,这是我进行更改之前不存在的代码.

I noticed that, after commenting the "release" part, the problem vanished and I was capable of compiling without errors; if the comment was erased, the problem returns. At the same time, while uncommented, I was able to notice that the release defines were defined despite the fact that I was in a debug compilation 'state'. And finally this was a code that didn't exist prior to my changes.

唯一出现的问题是:为什么qmake不能正确解释.pro文件?但是,我要再提一个问题.

The only question that arrives is: why isn't qmake being capable of interpreting the .pro file correctly? But I'll put that in another question.

感谢您的帮助,

这篇关于奇怪的“多个定义"类型错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆