В конструкторе
mySecondClass(myClass& reference)
{
myClassReference = reference; //doesn't get accepted by the compiler
};
используется ссылка myClassReference
, которая должна быть инициализирована при ее создании. Однако переменная не была инициализирована. Используется оператор копирования.
В этом конструкторе
mySecondClass(myClass& reference) : myObjectReference(reference){}
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
ссылка создается и инициализируется в списке mem-initializer.
Чтобы сделать его более понятным рассмотрим следующую демонстрационную программу.
#include <iostream>
struct Int
{
Int() { std::cout << "Int()\n"; }
Int( int x ) : x( x ) { std::cout << "Int( " << x << " )\n"; }
Int & operator =( int x )
{
std::cout << "Int & operator =( " << x << " )\n";
this->x = x;
return *this;
}
int x;
};
struct A
{
A( int x )
{
this->value = x;
}
Int value;
};
struct B
{
B( int x ) : value( x ) {}
Int value;
};
int main()
{
A a( 10 );
std::cout << '\n';
B b( 10 );
return 0;
}
Его вывод
Int()
Int & operator =( 10 )
Int( 10 )
То есть, когда тело конструктора A получает элемент управления, член данных уже был создан с использованием конструктора по умолчанию класс Int. В теле конструктора используется оператор присваивания.
В противоположность конструктору класса A конструктор класса B создал член данных в списке mem-inkitializer, используя конструктор класса Int. с параметром.
Итак, теперь представьте, что вы используете ссылку в классе A. Затем она «инициализируется по умолчанию», то есть фактически не инициализируется ни одним допустимым объектом, на который ссылается оболочка. Таким образом, в теле конструктора вы пытаетесь присвоить значение недопустимой ссылке, которая нигде не ссылается. Таким образом, компилятор выдает ошибку.