【问题标题】:Type having conversion to Type&& operator类型转换为 Type&& 运算符
【发布时间】:2015-01-26 06:27:03
【问题描述】:

我很惊讶地看到以下编译:

struct C {
    operator C&&() {
        std::cerr << "ref'd\n";
        throw std::runtime_error("what is happening?");
    }
};

一种类型,带有用于其自身的右值引用转换的运算符。但是,我无法使用我认为可以做到的方式调用操作员。将值传递给采用右值引用的函数失败,并且在对象上调用 std::move 不会触发任何事情。

为什么这段代码完全可以编译,有没有办法让这个函数真正运行?

clang 给出warning: conversion function converting 'C' to itself will never be used 有或没有类型上的引用。

【问题讨论】:

  • 对于operator C&amp;(),铿锵声的结果相同。问题立场。
  • 技术上不是不可调用的;您可以使用C c; c.operator C&amp;&amp;(); 或获取成员函数指针C &amp;&amp;(C::*ptr)() = &amp;C::operator C&amp;&amp;; 并使用它。它不会在远程健全的代码中使用。
  • @Wintermute 另一个例外是虚拟调度。
  • @reymabel 哦,对。它甚至在您答案部分的脚注中都这么说。

标签: c++ c++11


【解决方案1】:
struct C
{
    operator C()
    {
    }
};

也是允许的,并给出相同的警告。它在 §12.3.2/1 中提到:

从不使用转换函数来转换(可能 cv 限定)对象到(可能 cv 限定)相同的对象类型 (或对它的引用),到(可能是 cv 限定的)基类 该类型(或对其的引用),或(可能是 cv 限定的)void。

换句话说,它不是被禁止的,但它根本不做任何事情。 Yakk 和 Wintermute 已经展示了成员函数调用语法的示例,但 cppreference 展示了脚注 116 中提到的虚拟调度示例(N3337,N4140 中的脚注 118):

struct D;
struct B {
    virtual operator D() = 0;
};
struct D : B
{
    operator D() override { return D(); }
};

int main()
{
    D obj;
    D obj2 = obj; // does not call D::operator D()
    B& br = obj;
    D obj3 = br; // calls D::operator D() through virtual dispatch
}

【讨论】:

  • 轻微挑剔:这是脚注 116,而不是 118。
  • @Deduplicator 我认为如果绑定到 const 引用来延长临时对象的生命周期是非常没用的。
  • @BWG:如果在那种情况下复制省略是强制性的......并且我们从一开始就拥有自动类型推断,正如 Stroustroup 所希望的......无论如何,这是一个严肃的竞争者。跨度>
  • @Deduplicator 我完全不知道这意味着什么,在这种情况下不使用复制省略是不是不可能?
【解决方案2】:
void foo(C&&){}
int main(){
  C c;
  foo(c.operator C&&());
}

所以,基本上没用,但不完全。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-10-10
    • 2014-10-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-11-21
    • 1970-01-01
    相关资源
    最近更新 更多