当前位置: 首页 > 知识库问答 >
问题:

C++命名空间-嵌套命名空间的前向声明和可见性

班思源
2023-03-14

这是一个非常基本的问题,但实际上我从来没有自己定义过名称空间。我正在尝试将我的基于Qt的库中的类分组在各种名称空间中(并且还允许更容易的扩展而不发生名称冲突)。例如,主类(也表示库)属于顶级命名空间lib:

namespace lib {
    class LibClass;
}

这个libclass使用了一组其他名称空间和类,这些名称空间和类是在libclass的头文件中定义的,这些头文件包含在libclass的头文件中:

#include <QObject>
#include "libclass_global.h"
#include "Manager.h"
#include "Configurator.h"

namespace lib {
    class LibClass;
}

class LIBCLASSSHARED_EXPORT LibClass : public QObject {
    public:
        LibClass();
        ...
    signals:
        ...
    private slots:
        ...
    public slots:
        ...
    private:
        lib::core::communication::Manager manager;             // PROBLEM HERE
        lib::core::communication::Configurator configurator;   // PROBLEM HERE
}

其中Manager.h包含

namespace lib {
    namespace core {
        namespace communication {
            class Manager;
        }
    }
}

class Manager {
    public:
        Manager();
        ...
    private:
        ...
}

和configurator.h包含

namespace lib {
    namespace core {
        namespace communication {
            class Configurator;
        }
    }
}

class Configurator {
    public:
        Configurator();
        ...
    private:
        ...
}

类的内容在这里并不重要。

在编译时,我发现名称空间Q3dtp中的core没有命名类型。因此,根据我的理解,基本上我需要在libclass的头文件中使用前向声明,因为名称空间似乎并不包含在包含这些名称的头文件中(出于某种原因):

namespace lib {
    class LibClass;

    namespace core {
        namespace communication {
            class Manager;
            class Configurator;
        }
    }
}

问题是,现在我只限于指针,因为我正向声明managerconfigurator。我想避免在可能的情况下(不需要的情况下)动态分配东西。

所以这里的问题是我如何解决这个问题?我显然可以将我的所有类声明移动到同一个头,将它们的定义移动到同一个源文件。然而,这将使情况在未来相当难以维持。仅仅声明子名称空间似乎也不能解决问题--我知道这两个类都没有命名类型,而且libclass没有成员名

共有2个答案

鲍飞星
2023-03-14

当你做的时候

namespace ns {
  class cls;
};

class cls {
};

您先声明一个类型,然后定义另一个类型。您需要限定类名:

namespace ns {
  class cls;
};

class ns::cls {
};

随着C++17的出现,如果这对于嵌套名称空间来说太麻烦了,您可以执行以下操作:

namespace ns1::ns2::ns3 {

  class cls {
  };

}
严劲
2023-03-14

您对libclass的声明是错误的。应该是:

namespace lib {
    class LibClass;
}

class lib::LibClass {
    ...
};

namespace lib {
    class LibClass {
        ....
    };
}

目前,您正在声明lib::libclass和定义::libclass(两种完全不同的类)。

这也适用于你的其他类。

 类似资料:
  • 我有困难建立一个有3个类的结构。我不确定包含/转发声明。 下面的代码一直在编译,直到我在inclino.h中添加名称空间和枚举。我从Inclinomeasure.h收到“Inclino尚未声明”。 倾斜度。h 倾斜度 倾角读数.h 结构正确吗?如何访问其他类中的枚举? 提前道谢。 编辑:我修复了名称空间的问题,把它放在一个新的文件,包括由3类。但我似乎误用了include/forward声明。

  • 如何在命名空间中转发声明类。例如,下面是一个库的头文件,用户不需要知道私有的myPtr,所以当包含在头文件下面时,不需要包含boost头文件。那么我如何向前声明boost::shared_ptr以启用用户代码编译呢? MyClass.h

  • 主要内容:定义命名空间,using关键字,命名空间嵌套在 C# 中,可以将命名空间看作是一个范围,用来标注命名空间中成员的归属,一个命名空间中类与另一个命名空间中同名的类互不冲突,但在同一个命名空间中类的名称必须是唯一的。 举个简单的例子,在一个简单的 C# 程序中,假如我们要输出某些数据,就需要使用 ,其中 System 就是命名空间,而 Console 是类的名字,WriteLine 则是具体要使用方法。也就是说,如果要访问某个命名空间中的类,我

  • 一个中大型软件往往由多名程序员共同开发,会使用大量的变量和函数,不可避免地会出现变量或函数的命名冲突。当所有人的代码都测试通过,没有问题时,将它们结合到一起就有可能会出现命名冲突。 例如小李和小韩都参与了一个文件管理系统的开发,它们都定义了一个全局变量 fp,用来指明当前打开的文件,将他们的代码整合在一起编译时,很明显编译器会提示 fp 重复定义(Redefinition)错误。 为了解决合作开发

  • 假设这样一种情况,当一个班上有两个名叫 Zara 的学生时,为了明确区分它们,我们在使用名字之外,不得不使用一些额外的信息,比如他们的家庭住址,或者他们父母的名字等等。 同样的情况也出现在 C++ 应用程序中。例如,您可能会写一个名为 xyz() 的函数,在另一个可用的库中也存在一个相同的函数 xyz()。这样,编译器就无法判断您所使用的是哪一个 xyz() 函数。 因此,引入了命名空间这个概念,

  • 所以我对Qt和C++都是新手,但我想弄清楚下面的代码是怎么回事。 我有一个头文件和源文件charinfowindow。在我拥有的源文件中: 在头文件中 我试着找出这些代码在网上做什么,但我只是在找关于如何做的资源。 如果有人能告诉我,首先,这些代码是做什么的,其次,他们为什么这样做。不胜感激。 谢谢