为什么将Auto推导到INT而不是UINT16_T
Why auto is deduced to int instead of uint16_t
我有以下代码:
uint16_t getLastMarker(const std::string &number);
...
const auto msgMarker = getLastMarker(msg.number) + static_cast<uint16_t>(1);
static_assert(std::is_same<decltype(msgMarker), const int>::value, "Should fail");
static_assert(std::is_same<decltype(msgMarker), const uint16_t>::value, "Should not fail");
我希望第一个断言会失败,第二个断言不会。但是gcc 4.9.2
和clang 3.6
做相反的事情。如果我在代码中使用uint16_t而不是自动,则正确断言失败了,另一个成功。
P.S。最初,我只有1
,而不是static_cast<uint16_t>(1)
,并认为该问题是由于数字文字1
具有INT类型而引起的,但即使在此处进行明确施放后,错误的断言也失败了。
添加将对其操作数执行通常的算术转换,在这种情况下,这将导致操作数被促进到 int 由于整数促销也是 int 。
您可以使用 uint16_t 而不是自动迫使转换后退或在一般情况下可以使用static_cast
。
对于为什么将小于 int 的类型升级为较大类型的基本原理,请参阅为什么在C和C 中算术操作之前必须将简短转换为INT。
供参考,来自C 标准部分5.7
加法操作员:
[...]对操作数进行了通常的算术转换 算术或枚举类型[...]
和 5
extressions :
[...]否则,应在 两个操作数。 59 ,则应应用以下规则 到晋升的操作数[...]
和4.5
积分促销(强调矿山):
除布尔,char16_t,char32_t或 WCHAR_T 其整数转换等级(4.13)小于等级 如果int可以代表,则可以将int的int转换为int类型 源类型的所有值;否则,来源可以 被转换为unsigned int类型的序言
假设 int 大于16位。
算术操作在任何类型的类型上都不小于int
。因此,如果uint16_t
小于int
,则在执行添加之前,它将促进到int
(或可能匹配其他操作数以匹配其他操作数)的。
加法的结果将是晋升类型。如果您想要另一种类型,则必须在以后进行转换。
- 为什么在全局范围内使用"extern int a"似乎不行?
- int(c) 和 c-'0' 之间的区别。C++
- 从"int*"强制转换为"unsigned int"会丢失精度错误
- 为什么野牛仍在使用"int yylex(void)",却找不到"int yylex(YYS
- 有符号的int和int-有没有一种方法可以在C++中区分它们
- 请解释这句话(cout<<1+int((a<b)^((b-a)&1) )<<endl
- 是否可以从int转换为enum类类型
- 不能在初始值设定项列表中将非常量表达式从类型 'int' 缩小到'unsigned long long'
- 向量 <int> a {N, 0} 和 int arr a[N] = {0} 的时间复杂度有什么区别
- 'short int'持有的值溢出,但"自动"不会溢出?
- 如何在C++中将一个无符号的 int 转换为两个无符号的短裤?
- 调用'begin(int [n])'没有匹配函数
- 没有显式声明的int[]中的foreach
- 在c++中访问int到类对象的映射时出错
- 为什么我无法更改"set<set>"循环中的值<int>
- 长 长 int 不要 长 int 好
- C++程序在循环后给出奇怪的int值
- 如何计算数据类型的范围,例如int
- 如果"new int"返回"int*",那么为什么"new int[n]"不返回"int**"?
- c# P-Invoke:如何转换INT fun(BYTE *bStream, UINT16 *nCount, const