c++ - 序列点和方法链

标签 c++ method-chaining sequence-points

以下表达式通常用于演示 undefined 未指定的行为:

f() + g()

如果 f()g() 都对某些共享对象有副作用,那么行为是 undefined 未指定,因为执行情况不明。 f() 可以在 g() 之前计算,反之亦然。

现在我想知道当你在一个对象上链接成员函数时会发生什么。假设我有一个类的实例,该实例名为 obj,它有两个成员函数 foo()bar()两者都修改对象。这些函数的执行顺序不可交换。在另一个之前调用它们的效果与反过来调用它们的效果不同。两种方法都返回对 *this 的引用,以便它们可以像这样链接:

obj.foo().bar()

但这是未指定的行为吗?我在标准中找不到任何东西(诚然只是浏览)可以区分这个表达式和我在帖子顶部给出的表达式。两个函数调用都是完整表达式的子表达式,因此它们的执行顺序是未指定的。但肯定 foo() 必须首先被评估,以便 bar() 知道要修改哪个对象。

也许我遗漏了一些明显的东西,但我看不到序列点的创建位置。

最佳答案

f() + g()

这里的行为是unspecified(不是undefined),因为每个操作数的计算顺序(即每个函数被调用)是unspecified .

 obj.foo().bar();

这在 C++ 中是明确定义的。

来自 C++ ISO 标准的相关部分 §1.9.17 写道,

When calling a function (whether or not the function is inline), there is a sequence point after the evaluation of all function arguments (if any) which takes place before execution of any expressions or statements in the function body. There is also a sequence point after the copying of a returned value and before the execution of any expressions outside the function.

类似案例已在以下主题中进行了详细讨论:

关于c++ - 序列点和方法链,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5523244/

相关文章:

c++ - 共享库地址空间

c++ - 为什么在这种情况下没有调用我的虚函数实现?

c++ - QSet::find() 迭代器解引用出现 “cannot convert ‘this’ 指针”错误?

c++ - 从 const 成员函数返回 'this' 作为非常量

c - 如何检查 c 中未定义的行为?

c - 为什么这些构造使用增量前和增量后未定义的行为?

c++ - 将整数除以无符号长整数 - 是否存在编译时错误/警告?

javascript - 如何在 ProtoType 中使用 Promises *around* 回调进行方法链接

javascript - NodeJS promise 链 : reuse "then" and merge two promises

c - 这是未定义的行为还是正常输出