Почему был вызван оператор копирования? - PullRequest
0 голосов
/ 15 мая 2019

В последней строке myA = foo(myOtherB); функция возвращает тип объекта типа A, таким образом;это будет все равно, что сказать `myA = input, но почему используется конструктор копирования?

output:

B foo()
 A copy ctor //what calls this?
 A op=

Для вызова конструктора копирования нам придется использовать присвоениеоператор во время инициализации, такой как: B newB = myOtherB;

#include <iostream>
using namespace std;

class A {
public:
 A() { cout << "A ctor" << endl; }
 A(const A& a) { cout << "A copy ctor" << endl; }
 virtual ~A() { cout << "A dtor" << endl; }
 virtual void foo() { cout << "A foo()" << endl; }
 virtual A& operator=(const A& rhs) { cout << "A op=" << endl; }
};

class B : public A {
public:
 B() { cout << "B ctor" << endl; }
 virtual ~B() { cout << "B dtor" << endl; }
 virtual void foo() { cout << "B foo()" << endl; }
 protected:
 A mInstanceOfA; // don't forget about me!
};

A foo(A& input) {
 input.foo();
 return input;
}
int main() {
 B myB;
 B myOtherB;
 A myA;
 myOtherB = myB;
 myA = foo(myOtherB);
}

Ответы [ 2 ]

2 голосов
/ 15 мая 2019

В последней строке myA = foo(myOtherB); функция вернет тип объекта типа B

Не верно.Ваша функция возвращает объект типа A по значению.Это означает, что любое значение, которое вы передаете этому объекту, будет использовано для создания нового объекта этого точного типа.Другими словами:

int foo(float a) {
    return a + 0.5;
}

int u;

u = foo(9.3);

// u has a value of 10

Не ожидайте, что u будет содержать значение, которое int не может.

То же самое, если вы используете пользовательские типы:

A foo(A& input) {
 input.foo();
 return input; // this expression returns a new A
               // using the value of `input`
}

A myA;

myA = foo(myOtherB);

// why would `myA` be anything else than the value of an A?

Итак, что же здесь происходит?

B foo()
 A copy ctor //what calls this?
 A op=
A foo(A& input) {
 input.foo(); // prints B foo, virtual call. a reference to A that
              // points to an object of subclass type B

 return input; // copy `input` into the return value object
}

Затем вызывается оператор =.

0 голосов
/ 15 мая 2019

См. cppreference

В частности:

Конструктор копирования вызывается всякий раз, когда объект инициализируется (путем прямой инициализации или инициализации копирования) из другого объекта.объект того же типа (если только разрешение перегрузки не выберет лучшее соответствие или вызов не будет исключен), что включает

  • инициализация: T a = b;или T a (b) ;, где b относится к типу T;
  • передача аргумента функции: f (a);, где a относится к типу T, а f не имеет значения f (T t);
  • функция return: return a;внутри функции, такой как T f (), где a имеет тип T, у которого нет конструктора перемещения.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...