static_cast<T> 对 T& 做了什么?

What does static_cast<T> do to a T&?

所以我问了 并且我正在修补通过 static_cast 解决它。 (顺便说一句,它确实解决了问题,我只是不确定我是否理解为什么。)

代码中:

vector<int> foo = {0, 42, 0, 42, 0, 42};
replace(begin(foo), end(foo), static_cast<int>(foo.front()), 13);

static_cast 只是构造一个 R 值 int 吗?那和只是打电话有什么区别:

replace(begin(foo), end(foo), int{foo.front()}, 13);

编辑:

根据答案 static_cast 似乎构建了一个 R 值 inthttp://ideone.com/dVPIhD

但是这段代码 不能 在 Visual Studio 2015 上工作。这是编译器错误吗?在这里测试:http://webcompiler.cloudapp.net/

  1. 是的,它与int{...}相同,除非.front()返回了一个需要缩小转换的类型。在那种情况下,int(...) 将是相同的。

  2. 在程序员错误的情况下,静态转换做一些危险的事情的可能性要小一些,比如将指针转换为 int 比 int(...).

注意消除转换会导致未定义的行为,因为替换操作修改了前面的元素,这可能会破坏 std::replace

我会用

template<class T>
std::decay_t<T> copy_of(T&& t){return std::forward<T>(t); }

我在这里。

至于为什么这在 MSVC 中不起作用...

MSVC 可以帮助您将类型为 T 的变量转换为 T 并继续执行任何操作的情况。这会破坏您的代码。

您可以使用 compiler flag (/Zc:rvalueCast) 让 MSVC 不再破坏您的代码。

成员函数frontreturns对非空向量第一个元素的引用。

另一方面,标准算法 replace 声明为

template <class ForwardIterator, class T>
  void replace (ForwardIterator first, ForwardIterator last,
                const T& old_value, const T& new_value)

也引用第三个参数。因此,通常算法可以更改向量的第一个元素,因此算法对向量的其他元素的处理结果可能不正确。

使用static_cast创建了一个临时对象,不会被算法改变所以对向量的所有元素的处理都是正确的。

至于我,我建议在这种情况下使用关键字 auto 的 C++ 提案。例如

replace(begin(foo), end(foo), auto( foo.front() ), 13);