Tag: 未定义的行为

a ] = 1是否会产生未定义的行为?

这个C99代码是否产生未定义的行为? #include <stdio.h> int main() { int a[3] = {0, 0, 0}; a[a[0]] = 1; printf("a[0] = %d\n", a[0]); return 0; } 在语句a[a[0]] = 1; , a[0]都被读取和修改。 我看了ISO / IEC 9899的n1124草案。它说(在6.5expression式中): 在前一个序列点和下一个序列点之间,一个对象应该通过评估一个expression式来最多修改其存储值一次。 此外,先前的值应该是只读的,以确定要存储的值。 它没有提到读取对象来确定要修改的对象本身。 因此这个陈述可能会产生未定义的行为。 不过,我觉得很奇怪。 这实际上是否会产生未定义的行为? (我也想知道在其他ISO C版本中的这个问题。)

为什么a =(a + b) – (b = a)是交换两个整数的不好的select?

我偶然发现了这个代码,用于交换两个整数而不使用临时variables或使用按位运算符。 int main(){ int a=2,b=3; printf("a=%d,b=%d",a,b); a=(a+b)-(b=a); printf("\na=%d,b=%d",a,b); return 0; } 但是我认为这个代码在交换语句a = (a+b) – (b=a);有未定义的行为a = (a+b) – (b=a); 因为它不包含任何序列点来确定评估的顺序。 我的问题是: 这是一个可接受的解决scheme交换两个整数?

在绑定的未定义行为之外访问全局数组?

我今天刚刚在我的课堂上进行了一次考试 – 阅读C代码和input,如果程序实际运行,所需的答案就是屏幕上显示的内容。 其中一个问题宣称a[4][4]是一个全局variables,在该程序的一个点上,它尝试访问a[27][27] ,所以我回答了这样一个问题:“ 访问一个数组在外部是一个未定义的行为 “,但老师说a[27][27]的值为0 。 之后,我尝试了一些代码来检查“所有未初始化的golbalvariables是否设置为0 ”是否为真。 那么,这似乎是真的。 所以现在我的问题: 似乎已经清除了一些额外的内存并保留供代码运行。 预留多less内存? 为什么编译器会预留更多的内存,这是什么原因? 对所有的环境来说, a[27][27]是0吗? 编辑: 在该代码中, a[4][4]是唯一声明的全局variables, main()中有更多的局部variables。 我在DevC ++中再次尝试了这个代码 。 他们都是0 。 但是在VSE中这是不正确的,其中大多数值是0但有一些是Vyktor指出的随机值。

为什么这是一个未定义的行为?

我对这个问题的回答是这个function: inline bool divisible15(unsigned int x) { //286331153 = (2^32 – 1) / 15 //4008636143 = (2^32) – 286331153 return x * 4008636143 <= 286331153; } 它完美的工作在我的机器上用VS2008编译器,但是在这里根本不起作用。 有没有人有一个想法,为什么我在不同的编译器上得到不同的结果? unsigned溢出不是未定义的行为。 重要提示:经过一些testing,证实它比15分的剩余部分更快(但不是所有的编译器)

为什么printf(“%f”,0); 给未定义的行为?

语句printf("%f\n",0.0f); 打印0。 但是,语句printf("%f\n",0); 打印随机值。 我意识到我正在展示某种不确定的行为,但是我无法弄清楚为什么特别。 所有位都是0的float值仍然是一个有效值为0的float 。 float和int在我的机器上是相同的大小(如果甚至是相关的)。 为什么在printf中使用整数文字而不是浮点文字会导致这种行为?

为什么增强的GCC 6优化器打破实用的C ++代码?

GCC 6有一个新的优化器function :它假定this总是不为空,并基于this优化。 值范围传播现在假定C ++成员函数的这个指针是非空的。 这消除了常见的空指针检查, 但也打破了一些不合格的代码库(如Qt-5,Chromium,KDevelop) 。 作为一个临时的work-around -fno-delete-null-pointer-checks可以被使用。 错误的代码可以通过使用-fsanitize = undefined来识别。 更改文件清楚地表明这是危险的,因为它打破了令人吃惊的常用代码量。 为什么这个新的假设会打破实用的C ++代码呢? 有没有特定的模式,不小心或不知情的程序员依赖这种特定的未定义的行为? 我无法想象任何人if (this == NULL)因为这是不自然的写作。

为什么这个循环在某些平台上退出,而不是在其他平台上退出?

我最近开始学习C,我正在以C为主题的课。 我目前正在玩循环,我遇到了一些奇怪的行为,我不知道如何解释。 #include <stdio.h> int main() { int array[10],i; for (i = 0; i <=10 ; i++) { array[i]=0; /*code should never terminate*/ printf("test \n"); } printf("%d \n", sizeof(array)/sizeof(int)); return 0; } 在我的笔记本电脑上运行Ubuntu 14.04,这个代码不会中断。 它运行完成。 在我学校的电脑上运行CentOS 6.6,它也运行良好。 在Windows 8.1上,循环永远不会终止。 更奇怪的是,当我将for循环的条件编辑为: i <= 11 ,代码仅在运行Ubuntu的笔记本电脑上终止。 它永远不会终止在CentOS和Windows。 任何人都可以解释内存中发生了什么,以及为什么不同的操作系统运行相同的代码会产生不同的结果? 编辑:我知道for循环超出界限。 我正在故意的 我只是无法弄清楚在不同的操作系统和计算机上,行为是如何不同的。

为什么f(i = -1,i = -1)未定义的行为?

我正在阅读评估违规的顺序 ,他们给我一个困惑的例子。 1)如果标量对象的副作用相对于同一个标量对象上的另一个副作用未被sorting,则行为是不确定的。 // snip f(i = -1, i = -1); // undefined behavior 在这种情况下, i是一个标量对象 ,这显然意味着 算术types(3.9.1),枚举types,指针types,成员types指针(3.9.2),std :: nullptr_t和这些types的cv限定版本(3.9.3)统称为标量types。 在这种情况下,我不明白这个陈述是如何含糊不清的。 在我看来,无论是第一个还是第二个参数先评估, i最终为-1 ,两个参数也是-1 。 有人可以澄清? UPDATE 我非常感谢所有的讨论。 到目前为止,我很喜欢@ harmic的回答,因为它暴露了定义这个陈述的陷阱和错综复杂的问题,尽pipe它乍看之下多么直截了当。 @ acheong87指出了使用引用时出现的一些问题,但是我认为这与这个问题的不确定副作用方面是正交的。 概要 由于这个问题引起了很大的关注,我将总结一下主要的观点和答案。 首先,请允许我进行一个小小的分析,指出“为什么”可以有密切相关但意义不同的含义,即“为什么”,“ 为什么 ”,“为了什么目的 ”。 我将把他们所说的“为什么”的那些含义的答案分组。 为什么导致 这里的主要答案来自保罗·德雷珀 ( Paul Draper) , 马丁·J ( Martin J)提供了一个类似但不是广泛的答案。 Paul Draper的答案归结为: 这是未定义的行为,因为它没有定义什么行为。 就解释C ++标准所说的问题而言,答案总的来说非常好。 它也解决了一些相关的UB案例,如f(++i, […]

是printf的输出(“%d%d”,c ++,c); 还未定义?

我最近碰到一篇文章cout << c ++ << c ;?的正确答案是什么? 并想知道是否输出 int c = 0; printf ("%d %d", c++, c); 也是未定义的? 我在讲座中学过后缀和前缀运算符只有在得到分号后才增加数值。 所以根据我,输出0 0是正确的!

检测未定义行为的C ++实现?

C ++中的大量操作导致了未定义的行为,规范完全忽略了程序的行为应该是什么,并允许发生任何事情。 正因为如此,各种各样的情况下,人们的代码可以在debugging但不是释放模式下编译,或者在一个看起来不相关的变化发生之前,或者在一个机器上运行,而不是在另一个机器上运行。 我的问题是是否有一个实用程序查看C ++代码的执行情况,并标记程序调用未定义行为的所有实例。 虽然我们有像valgrind和检查过的STL实现这样的工具是很好的,但是它们并不像我想的那么强大 – 例如,如果你丢弃了仍然分配的内存,valgrind可能会产生错误的否定,例如,检查STL实现将不会捕获通过基类指针删除。 这个工具是否存在? 或者它甚至会有用吗? 编辑 :我知道,一般静态检查是否C ++程序可能会执行一些未定义的行为是不可判定的。 但是,可以确定一个特定的C ++ 执行是否产生未定义的行为。 做到这一点的一种方法是制作一个C ++解释器,按照spec中定义的定义遍历代码,在每个点确定代码是否有未定义的行为。 这不会检测到未在特定程序执行中发生的未定义行为,但会发现在程序中实际显示的任何未定义的行为。 这与TM确定TM是否接受一些input的图灵可识别性有关,即使它一般还是不可判定的。 谢谢!