C ++显式完整的用户定义转换

时间:2017-02-13 07:37:31

标签: c++ type-conversion c++14 user-defined-types

我有一个标志类,它只是一个整数的包装器,我想根据基础整数类型的转换规则实现显式转换为任意整数类型。

说我有这样的课程(忽略不相关的成员)

class Flags {
    unsigned int v;
    explicit operator unsigned int() { return v; }
}

我还能转换为除之外的整数类型吗

unsigned long long iflags = static_cast<unsigned long long>(flags);

而不是

unsigned long long iflags = static_cast<unsigned int>(flags);

或者我是否需要为每个整数类型明确定义转换运算符才能执行此操作?

注意我正在使用C ++ 14

我读过http://en.cppreference.com/w/cpp/language/cast_operator但看不到任何特定于整数类型的东西,这让我觉得我需要明确定义我想要避免的所有有效转换。我也很满意模板转换功能,如果无法转换为目标类型将会失败,注意我知道内部整数的最大值,即所有标志位都打开,作为宏/常量{{1}如果这是有用的话。

2 个答案:

答案 0 :(得分:1)

  

我还能转换为除之外的整数类型吗

unsigned long long iflags = static_cast<unsigned long long>(flags);

不,你不能。

以上相当于:

unsigned long long temp(flags);
unsigned long long iflags = temp;

第一行错误,因为flags无法隐式转换为unsigned long long

鉴于Flags的定义,初始化iflags的唯一合法C ++方法是使用:

 unsigned long long iflags = static_cast<unsigned int>(flags);

如果您从转换运算符

中删除explicit限定符
class Flags {
    unsigned int v;
    public:
       operator unsigned int() { return v; }
}

然后你可以使用

unsigned long long iflags = static_cast<unsigned long long>(flags);

答案 1 :(得分:1)

static_cast次尝试属于[expr.static.cast]/4,如果您可以static_cast<T>(e)对某些发明变量T t(e);进行t,则Flags大致表示Flags #39;在措辞中有一些有趣的舞蹈,以照顾保证的省略和C风格的演员奇怪,我们可以忽略它们。)

初始化由[dcl.init]/17.7控制,它表示你对unsigned long long的转换函数执行重载解析,并指向[over.match.conv],这可以说明候选人:< / p>

  

那些未隐藏在其中的非显式转换函数   [unsigned long long]和收益类型[Flags]或类型可以   通过标准转换转换为[unsigned long long]类型   序列是候选函数。对于直接初始化,那些   显式转换函数未隐藏在[unsigned long long]和。{   yield类型[explicit operator unsigned int()]或可以转换为的类型   具有资格转换的类型[unsigned long long]也是   候选职能。

你的static_cast既不会产生case "Case1": class obj1 = new class (); string abc = obj1.calc("100"); break; case "Case2": class2 obj2 = new class2 (); string abc = obj2.calc("100"); break; ,也不能通过资格转换转换为它的类型(这里不相关 - 转换仅适用于指针式事物);因此,它不是候选人。由于候选集是空的,因此重载解析失败,因此初始化格式不正确,public static void ProcessModel(object Model) { String abc = <oBJECT>.calc("100"); } 也是如此。