لماذا لا يستدعي رمز C ++ 0x هذا مُنشئ Move؟

StackOverflow https://stackoverflow.com/questions/1046801

  •  20-08-2019
  •  | 
  •  

سؤال

لسبب ما ، لا يستدعي الرمز التالي أبدًا 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;
};
هل كانت مفيدة؟

المحلول

يحتوي الكود الخاص بك على موقعين محتملين للمكان الذي قد يتوقع فيه المرء أن يتم استدعاء مُنشئ الحركة (ولكنه لا):

1) استدعاء الأمراض المنقولة جنسيا :: تحرك
2) أثناء المهمة.

بخصوص 1) ، يقوم STD :: Move بإجراء طاقم بسيط - لا ينشئ كائنًا من نسخة - إذا حدث ذلك ، فقد يتم الاحتجاج بمنشئ الحركة ، ولكن نظرًا لأنه يقوم بمجموع RVALUE بسيط ، فلن يتم الاحتجاج به . تعريف STD :: MOVE مشابه لـ static_cast<Event&&>(temp).

فيما يتعلق 2) ، فإن التهيئة والتعيين هي عمليتان مختلفتان تمامًا (على الرغم من أن بعض أشكال التهيئة تستخدم رمز "= '). يقوم الرمز الخاص بك بالتعيين وبالتالي يستخدم مشغل الواجب الافتراضي الذي يُعلن أنه يقبل مرجع const lvalue. نظرًا لأنك لا تقوم بتهيئة كائن حدث واحد أبدًا ، فلن ترى مُنشئًا نقلك يتم استدعاءه. إذا أعلنت عن مشغل مهمة نقل: Event& operator=(Event&& other), ، فإن الكود الحالي الخاص بك سوف يستدعيه أو إذا كتبت: Event a; Event tmp = move(a); مُنشئك ، كما هو مكتوب ، سيتم الاحتجاج به.

نصائح أخرى

أنت لا تستخدم مُنشئ الحركة. أعتقد أن المبادلة تنفذ شيئًا كهذا

Event a;
Event b;

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

تريد استخدام مشغل تعيين Move ، والذي لا يوجد في الكود الخاص بك ، لذلك يعود إلى مشغل تعيين النسخ.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top