相关疑难解决方法(0)

C++代码可以在C++ 03和C++ 11中有效但是做不同的事情吗?

C++代码是否可以符合C++ 03标准和C++ 11标准,但根据编译的标准,可以做不同的事情吗?

c++ language-lawyer c++11 c++03

294
推荐指数
7
解决办法
2万
查看次数

为什么常量表达式会排除未定义的行为?

我正在研究核心常量表达式*中允许的内容,这在C++标准草案的5.19 常量表达式2段中有所描述:

条件表达式是核心常量表达式,除非它涉及以下之一作为潜在评估的子表达式(3.2),但是未评估的逻辑AND(5.14),逻辑OR(5.15)和条件(5.16)操作的子表达式不考虑[注意:重载的运算符调用函数.-end note]:

并列出随后的子弹中的排除项并包括(强调我的):

- 具有未定义行为的操作 [注意:包括,例如,有符号整数溢出(第5条),某些指针算术(5.7),除零(5.6)或某些移位操作(5.8) - 结束注释];

?为什么常量表达式需要此子句来涵盖未定义的行为常量表达式是否有一些特殊的东西需要未定义的行为才能在排除中进行特殊划分?

拥有这个条款是否给了我们没有它的任何优势或工具?

作为参考,这看起来像广义常量表达式提案的最新修订版.

c++ sfinae undefined-behavior constexpr c++11

46
推荐指数
3
解决办法
2752
查看次数

为什么1 << 31改为在C++ 14中实现定义?

在2014年之前的所有C和C++版本中,写作

1 << (CHAR_BIT * sizeof(int) - 1)
Run Code Online (Sandbox Code Playgroud)

导致未定义的行为,因为左移定义为等效于连续乘法2,并且此移位导致有符号整数溢出:

结果E1 << E2E1左移位E2位置; 腾出的位用零填充.[...]如果E1有一个带符号的类型和非负值,并且结果类型中可以表示E1×2 E2,那么这就是结果值; 否则,行为未定义.

但是在C++ 14中,文本已经改变<<但不是为了乘法:

E1 << E2E1左移位E2位置; 空位是零填充的.[...]否则,如果E1有一个有符号类型和非负值,并且E1×2 E2可以在结果类型的相应无符号类型中表示,那么转换为结果类型的那个值就是结果值; 否则,行为未定义.

现在的行为与签名类型的超出范围分配相同,即[conv.integral]/3所涵盖的行为:

如果目标类型已签名,则如果可以在目标类型(和位字段宽度)中表示该值,则该值不会更改; 否则,该值是实现定义的.

这意味着它仍然是不可移植的1 << 31(在具有32位int的系统上).那么为什么在C++ 14中做出这种改变呢?

c++ bit-shift c++14

32
推荐指数
1
解决办法
2597
查看次数

当sizeof(int)== 4时,1 << 31在C中定义得很好

根据这个问题的答案:

E1 << E2的结果是E1左移E2位位置; 腾出的位用零填充.如果E1具有无符号类型,则结果的值为E1×2 E2,比结果类型中可表示的最大值减少一个模数.如果E1具有带符号类型和非负值,并且E1×2 E2可在结果类型中表示,那么这就是结果值; 否则,行为未定.

这似乎意味着1 << 31未定义.

但是,如果我使用,GCC不会发出警告1 << 31.它确实发出一个问题1 << 32. 链接

那是哪个呢?我误解了标准吗?海湾合作委员会有自己的解释吗?

c bit-shift undefined-behavior language-lawyer

25
推荐指数
3
解决办法
1924
查看次数

编译器是否允许在常量表达式中考虑未定义的行为?

我们知道导致未定义行为的操作不是核心常量表达式(C++标准草案第5.19节第2段)

在测试中我已经完成了两个clang并将constexpr中的gcc未定义行为视为错误,但是在左移右移的情况下它们是不一致的.例如,根据Shift操作符13段,所有这些被视为未定义行为的情况:5.8

constexpr int x1 =  1 << 33 ; //Assuming 32-bit int
constexpr int x2 =  1 << -1 ;
constexpr int x3 =  -1 << 1 ;
constexpr int x4 =  1 >> 33 ; //Assuming 32-bit int
constexpr int x5 =  1 >> -1 ;
Run Code Online (Sandbox Code Playgroud)

clang会产生错误(看到它):

error: constexpr variable 'x1' must be initialized by a constant …
Run Code Online (Sandbox Code Playgroud)

c++ gcc undefined-behavior language-lawyer c++11

5
推荐指数
1
解决办法
661
查看次数