在不提供对 class 构造函数的访问的情况下定义 class 的类似枚举的常量

Define enum-like constants of a class without providing access to the class constructor

在 Java 中,我可以定义具有多个成员和成员函数的枚举常量,但不提供 public 对枚举构造函数的访问权限,以便客户端代码无法创建枚举之外的枚举已经定义。

我想在 C++ 中模拟这种行为,并尝试这样做:

// Card ranks of a 52-card deck
class _CardRank {
public:
    _CardRank(int val, char repr) : val{ val }, repr{ repr } {};

    int get_val() { return val; };
    char get_repr() { return repr; };

private:
    int val;
    int repr;
};

namespace CardRank {
    const _CardRank C_2(0, '2');
    const _CardRank C_3(1, '3');
    const _CardRank C_4(2, '4');
    const _CardRank C_5(3, '5');
    const _CardRank C_6(4, '6');
    const _CardRank C_7(5, '7');
    const _CardRank C_8(6, '8');
    const _CardRank C_9(7, '9');
    const _CardRank C_T(8, 'T');
    const _CardRank C_J(9, 'J');
    const _CardRank C_Q(10, 'Q');
    const _CardRank C_K(11, 'K');
    const _CardRank C_A(12, 'A');
}

这给了我正在寻找的作用域常量,但是客户端代码仍然能够创建新常量。是否有任何惯用的解决方案,或者此设计模式对 C++ 无效?

您可以使用 class 作为 namespace 允许友谊:

class CardRank
{
private:
    friend class CardRankNamespace;
    constexpr CardRank(int val, char repr) : val{ val }, repr{ repr } {}

public:
    int get_val() const { return val; }
    char get_repr() const { return repr; }
private:
    int val;
    int repr;
};

class CardRankNamespace
{
public:
    static constexpr CardRank C_2{0, '2'};
    // ...
};

我能想到的最接近的解决方案是匿名结构:

namespace MyEnum
{
    constexpr struct
    {
        const int val;
        const char *rep;
    } Enum1{1, "1"},
      Enum2{2, "2"},
      Enum3{3, "3"};
}