在以下代码中,选择了重载f(int)
而不是f(unsigned)
。用clang 3.0和gcc 4.8测试。
enum E
{
};
E f(int);
int f(unsigned);
E e = f(E(0));
我对标准的阅读使我认为enum -> int
和enum -> unsigned
是相同的标准转换序列,两者都只包含整数转换。
[conv.integral]枚举类型的右值可以转换为整数类型的右值。
根据[over.best.ics],仅包含积分转换的标准转换序列的等级为“转换”。
[over.ics.rank]两个相同形式的隐式转换序列是无法区分的转换序列,除非以下规则之一适用:[...]
在比较两个标准转换序列时,所提到的规则似乎都不适用。
我错过了什么?
答案 0 :(得分:6)
C ++ 11:
[conv.prom] / 3
其基础类型未固定的无范围枚举类型的prvalue(7.2)可以转换为以下类型中的第一个的prvalue,它可以表示枚举的所有值(即,如7.2)中所述的b min到b max范围内的值:
int
,unsigned int
,long int
,unsigned long int
,long long int
或{{ 1}}。
(强调我的)
然后,[over.ics.rank] / 4:
标准转化顺序按其排名排序:完全匹配是比促销更好的转化,转化比转化更好。
因此,对于表达式unsigned long long int
的重载解析,重载f(E(0))
仅需要整数提升(从E f(int);
到E
,通过[conv.prom]) ,int
(从int f(unsigned);
到E
通过[conv.integral])所需的积分转换排名更高。
对于C ++ 03,论证是一样的,尽管第一个引用略有不同: [conv.prom] / 2
类型
unsigned
(3.9.1)或枚举类型(7.2)的rvalue可以转换为以下第一种类型的rvalue,它可以表示其基础类型的所有值:{{ 1}},wchar_t
,int
或unsigned int
。
[over.ics.rank] / 4是一样的。