【问题标题】:Where to put the enum in a cpp program?将枚举放在 cpp 程序中的什么位置?
【发布时间】:2009-06-15 05:29:39
【问题描述】:

我有一个使用枚举类型的程序。

enum Type{a,b,};


class A
{
 //use Type
};
class B
{
  // also use that Type
};

2 类位于 2 个不同的文件中。 我应该将类型定义放在头文件中还是 在每个类的类定义中?

【问题讨论】:

  • 不是同一个问题,恕我直言。
  • 我不确定它是否完全重复。这个问题是指一个不属于任何结构的枚举,但在两个类中使用。另一个问题是指在另一个结构中使用一个结构中的枚举。
  • 我认为这是同一个主题:“我应该将枚举声明放在一个类中并从另一个类中引用它,或者将它放在两个类中并从两者中引用它,或者将它放入一个通用的基类,还是……?”。我认为他们都有相同的答案,即使他们不是相同的原始问题。

标签: c++


【解决方案1】:

如果要在多个 .cpp 文件中使用枚举,则应将其放在每个将包含的头文件中。如果有一个通用的头文件,你应该使用它,否则你也可以为这个枚举创建一个新的头文件

【讨论】:

    【解决方案2】:

    您应该始终尝试限制 C++ 中类型的范围,因此枚举可能应该在类范围内声明。枚举通常比另一个更自然地属于一个类 - 假设是 A 类,所以你把它放在 a.h 标头中的 A 声明中:

    // a.h
    
    class A {
        public:
           enum Type { a, b };
        ...
    };
    

    现在您需要在声明 B 的标头中包含 a.h:

    // b.h
    #include "a.h"
    
    class B {
       public:
          void f( A::Type t );     // use the Type enum
       ...
    };
    

    【讨论】:

    • 这真的取决于情况。在类之外声明枚举本身并没有错,在许多情况下,这是一个首选的解决方案。请注意,您还应该尝试限制不需要的依赖项。
    • 无论是否在类中都会有依赖关系。查看我自己的代码,我没有发现在类之外声明枚举的任何情况。
    • 但是对你刚需要的东西(枚举)的依赖和对A类其余部分的依赖是有区别的,这是不相关的,违反了最少知识的原则。
    • 好吧,我们对 A 和 B 的了解还不够,无法说出任何有用的话。在我自己的代码中,如果一个类使用类枚举(并且我所有的枚举都是类枚举),它总是使用包含枚举的类的其他特性。但是YMMV。
    • 在不了解更多信息的情况下,我会说将枚举与 A 或 B 放在一起会产生不必要的接口依赖性。最好使 A 和 B 处于相同的依赖级别(都包括定义常量的单独标头等),除非类之间已经存在显式的 interface 依赖(而不是 implementation 依赖,这更容易处理)。
    【解决方案3】:

    我明白 Neil 的观点:对于许多程序员来说,看到全局范围内的东西是一件很讨厌的事情。 otoh,恕我直言,仅为枚举引入一个类不是一种好的风格:它应该是枚举而不是一个类。但是,在两个类中放置相同的枚举列表(这是您要问的)将是最糟糕的主意:我们不想重复一些东西。

    此外,在大多数非平凡代码中,最终可能会使用更多此类共享实体(更多枚举、常量参数等)来实现。因此,我将开始将所有这些集中到一个实现命名空间(比如“detail”)中,它是您的类的子命名空间,并驻留在一个单独的头文件(比如“detail.hpp”)中,被所有人包含。例如:

    // file A.hpp 
    #include "foo/detail.hpp"
    namespace foo {
       class A 
       { 
       // accessing enum as detail::a 
       };
    }
    
    // file B.hpp
    #include "foo/detail.hpp"
    namespace foo { class B { ... }; }  
    
    // file foo/detail.hpp
    namespace foo { namespace detail {
       enum { a,b, ... }
       const int three = 3;
       // etc...
       // other implementation classes etc...
    }}
    

    “详细信息”是一种很好且干净的方式,可以警告您的班级用户不要放弃其中声明的任何内容。随着您的代码变得越来越大并且这些实现细节的数量开始增加,您可以将依赖关系分解为单独的头文件(detail1 detail2 等...)并仍然保留一个“详细”命名空间(这是您无法使用“类详细信息”完成的事情) “ 例如)。

    【讨论】:

      【解决方案4】:

      这个问题相当模糊,但根据经验,您应该尽量减少代码中的冗余。因此,您应该将枚举的声明放在头文件中。

      【讨论】:

        【解决方案5】:

        这实际上取决于这些值是否具有相同的逻辑类型,或者它们是否恰好具有相同的名称。将 A::Type 变量分配给 C::Type 是否有意义?如果它们是相同的逻辑类型,则将它们放在两者都包含的标头中。为了缩短构建时间,您可能希望将其放在自己的头文件中,但如果您想减少文件数量,则将其放在与其他内容共享的头文件中。

        另一种选择是将枚举放在一个共同的基类中,这两者都继承自(这在这种情况下可能没有意义,但它是另一种选择)。

        【讨论】:

          猜你喜欢
          • 2019-06-23
          • 2011-10-23
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2018-01-03
          相关资源
          最近更新 更多