问题标签 [sequence-points]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
c - 这个程序有任何序列点问题吗?
j=(i++,++i,j*i);这个定义好了吗?让我清除我的疑问。
c++ - 涉及逻辑与 (&&) 的复杂表达式
我最近开始阅读有关序列点的内容,但我无法弄清楚上面的代码示例是否正常。我知道&&
运算符引入了一个序列点,所以我不太确定表达式 z = x && y && ++z 的行为。有人请告诉我正确的答案。
c++ - 未排序的值计算(又名序列点)
很抱歉再次打开这个话题,但是考虑这个话题本身已经开始给我一个未定义的行为。想要进入定义明确的行为区域。
给定
我认为上述表达式(按此顺序)为
现在谈到这里的行为是来自C++ 0x的重要引述。
$1.9/12-“表达式(或子表达式)的评估通常包括值计算(包括确定对象的身份以进行左值评估和获取先前分配给对象以进行右值评估的值)和副作用的启动。”
$1.9/15-“如果标量对象的副作用相对于同一标量对象的另一个副作用或使用同一标量对象的值的值计算是未排序的,则行为未定义。”
[注意:与不同参数表达式相关的值计算和副作用是无序的。——尾注]
$3.9/9-“算术类型 (3.9.1)、枚举类型、指针类型、指向成员类型的指针 (3.9.2)、std::nullptr_t 和这些类型的 cv 限定版本 (3.9.3) 统称为标量类型。”
在 Expr1 中,表达式
i
(第一个参数)的评估相对于表达式的评估operator++(i)
(具有副作用)是无序的。因此 Expr1 具有未定义的行为。
在 Expr2 中,表达式
i
(第一个参数)的评估相对于表达式operator++(i, 0)
(具有副作用)的评估是无序的。因此 Expr2 具有未定义的行为。
在 Expr3 中,
operator++(i)
需要在调用外部参数之前完成对单独参数的评估operator++
。因此,Expr3 具有明确定义的行为。
在 Expr4 中,表达式
i
(第一个参数)的计算相对于operator[](operator++(i, 0)
(有副作用)的计算是无序的。因此 Expr4 具有未定义的行为。
这种理解正确吗?
PS OP中分析表达式的方法不正确。这是因为,正如@Potatoswatter 所指出的那样 - “第 13.6 条不适用。请参阅 13.6/1 中的免责声明,“这些候选函数参与 13.3.1.2 中所述的运算符重载解决过程,并且不用于其他目的。 “它们只是虚拟声明;不存在与内置运算符相关的函数调用语义。”
c - 循环缓冲区中简洁索引处理的建议
我已经实现了一个循环缓冲区,我想要一种简洁的方法来更新缓冲区指针,同时正确处理环绕。
假设一个大小为 10 的数组,我的第一反应是这样的:
静态分析以及gcc -Wall -Wextra正确地拍打了我的手腕,因为由于序列点违规而导致的未指定行为。明显的修复是这样的:
但是,我一直在寻找更简洁的东西(即单线)来“封装”这个操作。建议?除了p++;p%= 10;:-)
c - 在 C99 中, f()+g() 是未定义的还是仅仅是未指定的?
我曾经认为在 C99 中,即使函数的副作用f
和g
干扰,虽然表达式f() + g()
不包含序列点,f
并且g
会包含一些,所以行为是未指定的:要么 f() 会在之前调用g() 或 g() 在 f() 之前。
我不再那么肯定了。如果编译器内联函数(即使未声明函数,编译器也可能决定这样做inline
)然后重新排序指令怎么办?可以得到与上述两者不同的结果吗?换句话说,这是未定义的行为吗?
这不是因为我打算写这种东西,这是为了在静态分析器中为这样的语句选择最佳标签。
c - 是“int i = x++, j = x++;” 合法的?
我想,标题很清楚。我对此并不完全确定,而且我无法通过谷歌找到一个好的答案(唉,我还没有致力于标准的艺术),所以我问:
这是定义的吗?我很确定i = x++, j = x++;
作为一个正常的语句将是未定义的行为是逗号运算符,它是一个序列点并且是合法的,但是没有来源很清楚初始化程序是以分号结束还是下一个变量开始被声明,并且由于这不是使用的逗号运算符,因此我找不到明确的答案。所以要么a)逗号结束初始化程序,是一个序列点,并且有效,要么b)它没有。它是哪一个?
为了排除,我知道我应该简化头痛并将其写为:
并保证它已定义。出于好奇,我问得更多。
c++ - 关于序列点的解释
最近,我看到很多关于输出的问题被问到一些疯狂但在语法上允许的代码语句,比如 likei = ++i + 1
和i=(i,i++,i)+1;
。老实说,在实际编程中几乎没有人写过这样的代码。坦率地说,在我的专业经验中,我从未遇到过任何这样的代码。所以我通常最终会在 SO 上跳过这些问题。但最近,被问到的此类 Q 的数量之多让我想,如果我跳过此类 Q,是否错过了一些重要的理论。我认为这样的 Q 围绕着Sequence points
. 坦率地说,我几乎对序列点一无所知,我只是想知道不知道它是否在某种程度上是一个障碍。那么有人可以解释一下理论/概念吗Sequence points
,或如果可能,请指向解释该概念的资源。此外,是否值得花时间了解这个概念/理论?
c++ - 为什么这是未定义的行为?
为什么以下给定表达式会调用未定义的行为?
我的问题受这里Als 问题的影响
c++ - 未定义的行为和序列点
什么是“序列点”?
未定义的行为和序列点之间的关系是什么?
我经常使用有趣而复杂的表达方式,例如a[++i] = i;
,让自己感觉更好。为什么我要停止使用它们?
如果您已阅读本文,请务必访问后续问题Undefined behavior and sequence points reloaded。
(注意:这是对Stack Overflow 的 C++ FAQ 的一个条目。如果您想批评以这种形式提供 FAQ 的想法,那么开始这一切的 meta 上的帖子就是这样做的地方。该问题在C++ 聊天室中进行监控,FAQ 想法最初是从那里开始的,因此您的答案很可能会被提出该想法的人阅读。)c - gcc 的 -Wsequence-point 警告标志是否损坏?
我收到此行的警告:
将 移动++s
到单独的语句会使警告消失,但据我所知,这个警告是完全不正确的。的值s
仅在 的计算中使用一次++s
。第二种用途s
只是取其地址。有什么我想念的吗?