1

假设我有一个 MessageBox 类,如下所示:

class MyMessageBox
{
public:
    enum Priority {
        Prior_Dialog,
        Prior_Warning,
        // ...
    };

    enum Icon {
        Icon_Question,
        Icon_Exclamation,
        // ...
    };

    enum Button {
        Button_Yes,
        Button_No,
        Button_Cancel,
        // ...
    };

    static void Show(Priority pPriority, Icon pIcon, Button pButton1, Button pButton2);

    // ...
};

现在,如果我想抛出一个消息框,我必须MyMessageBox::为每个标识符输入:

MyMessageBox::Show(MyMessageBox::Prior_Dialog, MyMessageBox::Icon_Question, MyMessageBox::Button_Yes, MyMessageBox::Button_No);

理想情况下,我想要一些非宏解决方案,它允许源文件在任何地方#include "MyMessageBox.h"省略MyMessageBox::限定条件。这可能吗?

4

5 回答 5

7

是的,而且很简单。如果您不希望enums 在类中,那么...不要在类中定义它们。

enum Priority {
    Prior_Dialog,
    Prior_Warning,
    // ...
};

enum Icon {
    Icon_Question,
    Icon_Exclamation,
    // ...
};

enum Button {
    Button_Yes,
    Button_No,
    Button_Cancel,
    // ...
};

class MyMessageBox
{
public:
    static void Show(Priority pPriority, Icon pIcon, Button pButton1, Button pButton2);
// ...
};
于 2012-08-14T18:41:16.390 回答
4

如果枚举和类在单独的命名空间中声明(即枚举应该在类之外声明)只是为了不污染全局命名空间,也许会很方便。

namespace MessageBoxUtils {

enum Priority {
    Prior_Dialog,
    Prior_Warning,
    // ...
};

enum Icon {
    Icon_Question,
    Icon_Exclamation,
    // ...
};

enum Button {
    Button_Yes,
    Button_No,
    Button_Cancel,
    // ...
};

class MyMessageBox
{
public:
    static void Show(Priority pPriority, Icon pIcon, Button pButton1, Button pButton2);

    // ...
};

} // namespace MessageBoxUtils

客户端代码(一些 cpp 文件):

#include ...

using namespace MessageBoxUtils;

...

void SomeClass::Foo()
{
    MyMessageBox::Show(Prior_Dialog, Icon_Question, ...);
}
于 2012-08-14T18:56:52.093 回答
1

如果您想在类之外定义枚举,并且您还想避免重复并避免枚举名称冲突的风险,请考虑 C++11 的enum class可能性:

重新制作 Luchian Grigore 样本

enum class Priority {
    Dialog,
    Warning,
    // ...
};

enum class Icon {
    Question,
    Exclamation,
    // ...
};

enum class Button {
    Yes,
    No,
    Cancel,
    // ...
};

您现在被迫通过显式限定枚举来使用枚举,例如等Button::YesIcon::Question并且您还被迫显式转换为 int(不存在隐式转换)

于 2012-08-14T19:41:35.930 回答
0

You cannot "import" identifiers into the global namespace by means of the using keyword:

using MyMessageBox::Prior_Dialog; // won't work

(The first glance on the documentation misled me: http://msdn.microsoft.com/en-us/library/was37tzw%28v=vs.80%29.aspx)

Still, I would recommend leaving the enums where they belong -- in the MessageBox class. This avoids confusion and ambiguities -- someone else could define the same enum item but assign it a different value, leading to a compilation error.

Alternatively, you could change the class into a namespace, and then "load" identifiers (or even the whole namespace, if you wish), using using.

Other possible shortcuts include:

  • typedefing the enum inside the MessageBox class to a short convenient identifier and use this as qualification (hacky)

  • Copying individual constants into your namespace as they are required (cumbersome)

  • ...?

于 2012-08-14T18:46:45.140 回答
0

另一种选择是将您的枚举放入与您的小部件相关的完全不同的命名空间中。Qt例如,图书馆就是这样做的。他们将大量枚举放在Qt命名空间中,而不是将它们放在特定的类中

于 2012-08-14T18:55:24.937 回答