В результате только члены класса Shape
Shape
, используя операции копирования, заданные по умолчанию. Это общая идиома, предотвращающая непредвиденное копирование. Рассмотрим пример.void my_fct(const Open_polyline& op, const Circle& c)
{
Open_polyline op2 = op; // ошибка: копирующий конструктор
// класса Shape закрыт
vector
v.push_back(c); // ошибка: копирующий конструктор
// класса Shape закрыт
// ...
op = op2; // ошибка: присваивание в классе
// Shape закрыто
}
push_back()
push_back()
помещает в вектор my_fct()
. Мы не можем копировать объект класса Circle
в вектор v
, содержащий объекты типа Shape
; объект класса Circle
имеет радиус, а объект класса Shape
— нет, поэтому sizeof(Shape) . Если бы мы допустили операцию v.push_back(c)
, то объект класса Circle
был бы “обрезан” и любое последующее использование элемента вектора v
привело бы к краху; операции класса Circle
предполагают наличие радиуса (члена r
), который не был скопирован.Конструктор копирования объекта op2
op
имеют тот же самый недостаток. Рассмотрим пример.Marked_polyline mp("x");
Circle c(p,10);
my_fct(mp,c); // аргумент типа Open_polyline ссылается
// на Marked_polyline
Теперь операции копирования класса Open_polyline
mark
, имеющего тип string
. Shape
Срезка (да, это технический термин) — не единственная причина, по которой следует предотвращать копирование. Существует еще несколько понятий, которые лучше представлять без операций копирования. Напомним, что графическая система должна помнить, где хранится объект класса Shape
Shape
с объектами класса Window
, а не копируем их. Объект класса Window
ничего не знает о копировании, поэтому в данном случае копия действительно хуже оригинала. clone()
clone()
можно написать, только если функций для чтения данных достаточно для реализации копирования, как в случае с классом Shape
. 14.3. Базовые и производные классы
Посмотрим на базовый и производные классы с технической точки зрения; другими словами, в этом разделе предметом дискуссии будет не программирование, проектирование и графика, а язык программирования. Разрабатывая нашу библиотеку графического интерфейса, мы использовали три основных механизма.
Circle
является производным от класса Shape
, иначе говоря, класс Circle
является разновидностью класса Shape
или класс Shape
является базовым по отношению к классу Circle
. Производный класс (в данном случае Circle
) получает все члены базового класса (в данном случае Shape
) в дополнение к своим собственным. Это свойство часто называют