相关疑难解决方法(0)

为什么这个循环产生"警告:迭代3u调用未定义的行为"并输出超过4行?

编译:

#include <iostream>

int main()
{
    for (int i = 0; i < 4; ++i)
        std::cout << i*1000000000 << std::endl;
}
Run Code Online (Sandbox Code Playgroud)

gcc产生以下警告:

warning: iteration 3u invokes undefined behavior [-Waggressive-loop-optimizations]
   std::cout << i*1000000000 << std::endl;
                  ^
Run Code Online (Sandbox Code Playgroud)

我知道有一个有符号的整数溢出.

我不能得到的是为什么i价值被溢出操作打破了?

我已经阅读了为什么x86上的整数溢出与GCC导致无限循环的答案,但我仍然不清楚为什么会发生这种情况 - 我认为"未定义"意味着"任何事情都可能发生",但这种特定行为的根本原因是什么?

在线:http://ideone.com/dMrRKR

编译: gcc (4.8)

c++ gcc undefined-behavior

160
推荐指数
5
解决办法
6万
查看次数

自C++ 17以来,具有正确地址和类型的指针仍然始终是有效指针吗?

(参考这个问题和答案.)

在C++ 17标准之前,[basic.compound]/3中包含以下句子:

如果类型T的对象位于地址A,则类型为cv T*的指针(其值为地址A)被称为指向该对象,而不管该值是如何获得的.

但是自从C++ 17以来,这句话已被删除.

例如,我相信这句话使这个示例代码定义,并且从C++ 17开始这是未定义的行为:

 alignas(int) unsigned char buffer[2*sizeof(int)];
 auto p1=new(buffer) int{};
 auto p2=new(p1+1) int{};
 *(p1+1)=10;
Run Code Online (Sandbox Code Playgroud)

在C++ 17之前,p1+1保持地址*p2并具有正确的类型,因此*(p1+1)是指向*p2.在C++中,17 p1+1是一个指向前端指针,所以它不是指向对象指针,我相信它不是可以解除引用的.

对标准权的这种修改的解释是否还有其他规则来补偿所引用的句子的删除?

c++ pointers language-lawyer c++14 c++17

80
推荐指数
2
解决办法
4177
查看次数

数组外的指针比较的基本原理是UB

因此,标准(参考N1570)说明了以下关于比较指针的内容:

C99 6.5.8/5关系运算符

比较两个指针时,结果取决于指向的对象的地址空间中的相对位置.... [在聚合中剪切明显的比较定义] ... 在所有其他情况下,行为未定义.

这个UB实例的基本原理是什么,而不是指定(例如)转换intptr_t和比较它?

是否存在一些机器架构,其中指针的合理总排序难以构建?是否存在一些优化或分析,不受限制的指针比较会阻碍?

这个问题的删除答案提到这条UB允许跳过段寄存器的比较并且仅比较偏移.保存特别有价值吗?

(同样删除的答案,以及此处的答案,请注意,在C++中,std::less需要对指针实现总顺序,无论正常比较运算符是否执行.)

c pointers undefined-behavior language-lawyer

6
推荐指数
1
解决办法
446
查看次数

标签 统计

c++ ×2

language-lawyer ×2

pointers ×2

undefined-behavior ×2

c ×1

c++14 ×1

c++17 ×1

gcc ×1