温馨提示:本文翻译自stackoverflow.com,查看原文请点击:其他 - Qt C++: Multiple Q_NAMESPACE for the same namespace in different files
c++ QT

其他 - Qt C ++:不同文件中同一命名空间的多个Q_NAMESPACE

发布于 2020-04-08 11:51:45
  • 我有两个enum秒。它们在相同的名称空间中,但是头文件不同。
  • 为了使它们可用于Qt元类型系统,我尝试这样做:
//C1.h
#include <QObject>
namespace SW
{
Q_NAMESPACE
enum class Enum1 {A, B};
Q_ENUM_NS(Enum1)
}
//C2.h
#include <QObject>
namespace SW
{
Q_NAMESPACE
enum class Enum2 {A, B};
Q_ENUM_NS(Enum2)
}
//main.c
#include <QDebug>
#include <QMetaEnum>

#include "C1.h"
#include "C2.h"

int main(int argc, char *argv[]) {
    auto me1 = QMetaEnum::fromType<SW::Enum1>();
    qDebug() << "me1 valid:" << me1.isValid();

    auto me2 = QMetaEnum::fromType<SW::Enum2>();
    qDebug() << "me2 valid:" << me2.isValid();
}
  • 有了以上我得到重复的符号链接器错误。因为这两个moc_C1.omoc_C2.o限定的staticMetaObject从该结果Q_NAMESPACE
  • 我发现两个标头中的名称空间都必须包含Q_NAMESPACE否则,moc会抱怨“错误:命名空间声明缺少Q_NAMESPACE宏。”
  • 如果我只有C1.h或C2.h中的一个,它将生成并正常工作。
  • 如果我将C2.h的内容移动到C1.h,它也可以工作,并且会打印:
me1 valid: true
me2 valid: true
  • 如果我将C2.h的内容移动到main.cpp(带有或不带有Q_NAMESPACE),它将编译但在运行时出现故障:
me1 valid: true
me2 valid: false

问题:没有办法Q_NAMESPACE用于分散在多个文件中的名称空间吗?

方法这项工作围绕这个问题,我能想到的:

  • 将我的枚举放在Q_OBJECT或Q_GADGET类中
  • 将我的所有枚举都放在同一个文件中

查看更多

提问者
twj
被浏览
220
138k 2020-02-01 09:38

根据他们的问题跟踪器QTBUG-68611,这似乎是一个已知的错误。

在解决此限制之前,我们将不得不忍受这一限制。

或者,您可以(尽管我不建议)在中间插入这样的文件结构:

// internal/C1.h
#include <QObject>
enum class Enum1 {A, B};
Q_ENUM_NS(Enum1)
//internal/C2.h
#include <QObject>
enum class Enum2 {A, B};
Q_ENUM_NS(Enum1)
// C.h
#include <QObject>
namespace SW
{
Q_NAMESPACE
#include internal/C1.h
#include internal/C2.h
}