4

出于某种原因,以下代码从不调用Event::Event(Event&& e)

Event a;
Event b;
Event temp;
temp = move(a);
a = move(b);
b = move(temp);

为什么不?

使用std::swap调用它一次。

class Event {
public:
    Event(): myTime(0.0), myNode(NULL) {}
    Event(fpreal t, Node* n);
    Event(Event&& other);
    Event(Event const& other) = delete;
    ~Event();

    bool                operator<(Event const& other) const { return myTime < other.myTime; }
    bool                operator>(Event const& other) const { return myTime > other.myTime; }
    fpreal              getTime() const { return myTime; }
    void                setTime(fpreal time) { myTime = time; }
    Node*               getNode() const { return myNode; }

private:
    fpreal              myTime;
    Node*               myNode;
};
4

2 回答 2

11

您没有使用移动构造函数。我认为交换是这样实现的

Event a;
Event b;

Event temp(move(a)); // this one wants to use a move constructor
a = move(b);
b = move(temp);

您想使用代码中不存在的移动赋值运算符,因此它回退到复制赋值运算符。

于 2009-06-26T00:38:00.090 回答
10

您的代码有两个可能的位置,人们可能期望调用移动构造函数(但它没有):


1 ) 在分配期间调用 std::move 2)。

关于 1),std::move 进行了简单的强制转换——它不会从副本创建对象——如果这样做了,则移动构造函数可能会被它调用,但由于它进行了简单的右值强制转换,因此不会被调用. std::move 的定义类似于static_cast<Event&&>(temp).

关于 2),初始化和赋值是两个完全不同的操作(尽管某些形式的初始化使用了 '=' 符号)。您的代码进行赋值,因此使用声明为接受 const 左值引用的默认赋值运算符。由于您从不使用另一个事件对象初始化一个事件对象,因此您不会看到调用移动构造函数。如果您声明了一个移动赋值运算符:Event& operator=(Event&& other),那么您当前的代码将调用它,或者如果您编写:Event a; Event tmp = move(a);您的移动构造函数,如所写,将被调用。

于 2009-06-26T00:37:24.803 回答