如何在类内部定义枚举并从外部使用它

Posted

技术标签:

【中文标题】如何在类内部定义枚举并从外部使用它【英文标题】:how to define an enumeration inside a class and use it from the outside 【发布时间】:2011-06-18 21:48:20 【问题描述】:

只是因为我不知道在我的 c++ 书中或在 google 上的确切位置。我如何在一个类中实际定义一些枚举(在本例中为 left=1, right=2, top=3, bottom=4 )。我希望能够将此枚举作为参数而不是整数传递给成员函数,因此在外部使用枚举...

有什么方法可以做到这一点,还是有更好的方法可以使枚举只针对该类?

这里的代码不起作用,出于某种原因说enum mySprite::<unamed> myySprite::side member mySprite "mySprite::side" is not a type name

class mySprite : public sf::Sprite

public:
    enumleft=1, right=2, top=3, bottom=4 side;

    float GetSide(side aSide)
        switch(aSide)
            // do stuff
        
    ;
;

【问题讨论】:

遗憾的是,当您无法更改定义 mySprite 的头文件时,没有一个答案解释了如何键入它。它来自第 3 方。另见c++ typedef another class's enum? 【参考方案1】:

让您的代码工作所需的最简单的更改是:

class mySprite : public sf::Sprite

public:
    enum side left=1, right=2, top=3, bottom=4 ;

    float GetSide(side aSide)
    
        switch(aSide)
        
            // do stuff
            // add breaks; as appropriate
            case left:
            case right:
            case top:
            case bottom:
        
    
;

你也可以这样做:

    typedef enum left = 1, right, top, bottom side;

这意味着为您的 mySprite 类定义一个匿名枚举类型,并使 side 成为一个别名,从而有效地完成与上述代码相同的事情。为了简洁起见,只需要为第一个枚举值分配一个起始整数。除非您明确指定其他值,否则该点之后的所有值都被理解为每次递增 1。

【讨论】:

+1,至少这个在语法上是正确的! (顺便说一句,第三种选择是:typedef enum side left=1, right, top, bottom side; 虽然这是第三种选择,但它在 C++ 中也是多余的。从技术上讲,typedef 本身在 C++ 中是多余的(在这种情况下),但它最终并不重要。无论哪种方式,编译器都应该足够聪明以理解它。 :) @david 我很惊讶 OP 接受了一个语法错误的答案。一个兼容的编译器只会拒绝该代码并给他更多的错误来处理。 @Chrono Kitsune:这不是完全多余的,只是枚举名称或 typedef 之间存在差异。 C 和 C++ 查找之间的区别在于,在通用标识符空间中找不到名称后,在 C++ 中会检查用户定义类型标识符空间。如果您有兴趣,我可以挖掘更长的解释(或在 SO 中找到一个) 不,谢谢。我相信你是完全正确的。毕竟,按照你说的去做是有意义的。谢谢你提供的详情。 :)【参考方案2】:

我认为这个例子说明了一切:

class A 
public:
    enum directions  top, left, right, bottom ; // directions is the type
                                                  // of the enum elements

    void f(directions dir) 
        if (dir == left) 
            // ...
         else 
            // ...
        
    
;

A object;
object.f(A::top);

【讨论】:

不,它没有,因为枚举默认是私有的:) 呃,让我到了那里,但是哈哈,你忘了我在课程的末尾忘记了一个分号(现在已经删掉了)。 另外,由于您使用的是枚举,您可能希望使用switch 而不是if Space_C0wb0y:不相关且不重要。 @nightcracker:语法错误,您在类中声明了一个未命名枚举类型的单个成员 directions。函数 void f( directions ); 不正确,因为 directions 不是类型。您可能的意思是:enum directions ... ;【参考方案3】:

您需要将其定义为一种类型,以便在类之外使用它和/或对参数进行强类型化。否则简单定义为int,其访问修饰符也必须是public:

 
class foo 
public:
    typedef enum DIRECTION 
        LEFT = 1,
        RIGHT,
        TOP,
        BOTTOM,
    ;
    void SetDirection(foo::DIRECTION dir) 
        _direction = dir;
    
    //...
protected:
    //...
private:
    foo::DIRECTION _direction;
    //...
;

int main() 
    //...
    foo bar;
    bar.SetDirection(foo::BOTTOM);
    //...


 

【讨论】:

@Casey,除了不需要之外,它还缺少类型定义的名称。您应该使用:enum DIRECTION ... ;typedef enum DIRECTION ... XXX;,其中 XXX 可能是 DIRECTION 或您想要提供的任何其他名称,但 typedef 语法 需要该名称。 @Lutz:我不知道是谁告诉你的,但所有 typedef 需要的是一个类型,即“enum”和同义词,即“DIRECTION ... ”。您所指的“XXX”是可以创建的可选变量。如果没有使用它并像示例中那样留空,则不会创建任何变量。 @Casey:XXX 不是可选变量的名称,而是 typedef-name (§7.1.3),它是新的 别名类型的名称。我已经在三个编译器(g++4.2、clang++ 和 comeau)中检查了代码,其中两个 warn 但都接受了代码。如果存在typedef,我无法确认类型定义中是否需要typedef-name,但由于它被编译器接受,因此它可能是可选的。有趣的是,警告是:warning: typedef requires a name,我认为如果它是required,如果缺少它应该是一个错误 idk 但是这段代码在 msVS++ 中对我有用....会出现其他问题吗?

以上是关于如何在类内部定义枚举并从外部使用它的主要内容,如果未能解决你的问题,请参考以下文章

在类中如何实现类的嵌套

使用内部枚举类作为外部类的参数的Mybatis的参数该如何判断

5.内部类

Java内部类

java 枚举数组的问题

如何在类向量中存储/使用外部函数指针