17

我试图std::swap从 [C++11:utility.swap] 中了解条件。模板定义为

template <typename T> void swap(T &, T &)

(加上一些noexcept细节)并具有“交换存储在两个位置的值”的效果。

以下程序是否已明确定义?

#include <utility>

int main()
{
    int m, n;
    std::swap(m, n);
}

如果我自己编写交换代码(即int tmp = m; m = n; n = tmp;),它将具有未定义的行为,因为它会尝试对未初始化的对象进行左值到右值的转换。但是标准std::swap函数似乎并没有附加任何条件,也不能从规范中得出存在任何左值到右值和因此 UB 的规范。

标准是否需要std::swap对未初始化的对象执行一些明确定义的魔法?

为了澄清这一点,请考虑函数void f(int & n) { n = 25; },它永远不会有未定义的行为(因为它不从 读取n)。

4

2 回答 2

12

非常好的问题。但是,我会说 [res.on.arguments]§1 涵盖了这一点:

除非另有明确说明,否则以下各项均适用于 C++ 标准库中定义的函数的所有参数。

  • 如果函数的参数具有无效值(例如函数域之外的值或对其预期用途无效的指针),则行为未定义。

为了解决您对 的担忧f(n),您问题中的函数f不是 C++ 标准库的一部分,因此上述条款不适用于它。

于 2014-06-20T21:39:53.523 回答
1

由于 M 的值未定义,我希望它会污染对交换的调用。当调用交换时,鼻魔可能会飞。

于 2014-06-20T21:39:33.670 回答