|
Программирование >> Разработка устойчивых систем
class Right : virtual public Top { int z: protected: void specialPrint(ostream& os) const { Выводятся только данные Right OS . z: public: Right(int m. int n) : Top(m) { z = n: } friend ostream& operator (ostream& os. const Right& r) { return OS static cast<const Top&>(r) . r.z: class Bottom : public Left, public Right { int w: public: Bottom(int i, int j. int k. int m) : Top(i). Left(0. j). Right(0. k) { w = m: } friend ostream& operator (ostream& os. const Bottoms b) { OS static cast<const Top&>(b): b.Left::specialPrint(os): b.Right::specialPrintCos): return OS . b.w: int mainO { Bottom b(l. 2. 3. 4): cout b endl: 1.2.3.4 } III:- Функции specialPrintO объявлены защищенными, потому что они будут вызываться только из Bottom. Они выводят лишь собственные данные, игнорируя данные подобъекта Тор, потому что вызов этих функций находится под контролем оператора класса Bottom. Последний должен знать о существовании виртуального базового класса, по аналогии с конструктором Bottom. Аналогичные рассуждения применимы к операторам присваивания в иерархиях с виртуальным базовым классом, а также к любым функциям (как функциям классов, так и внешним), выполняющим совместную работу во всех классах иерархии. После обсуждения виртуальных базовых классов можно показать настоящую процедуру инициализации объектов. Поскольку виртуальные классы порождают совместно используемые подобъекты, логично, что эти объекты должны быть доступны до того, как они начнут использоваться. Следовательно, инициализация подобъектов должна выполняться в следующем порядке (с рекурсией). 1. Инициализация всех подобъектов виртуальных базовых классов в порядке сверху вниз, слева направо по отношению к их расположению в определениях классов. 2. Инициализация подобъектов невиртуальных базовых классов в обычном порядке. return OS static cast<const Тор&>(1) . l.y: class С { M m: public: C(const strings s) : mCin C ) { cout C s endl: virtual -CO {} class D { M m: public: D(const strings s) : mCin D ) { cout D s endl: virtual -DO {} class E : public A. virtual public B. virtual public С { M m: 3. Инициализация вложенных объектов в порядке объявления. 4. Выполнение конструктора для всего объекта. Следующая программа показывает, как это происходит: : C09:VirtInit.cpp Порядок инициализации объектов при наличии виртуальных базовых классов #include <iostream> #include <str1ng> using namespace std: class M { public: M(const strings s) { cout M s endl: class A{ M m: public: A(const strings s) : mCin A ) { cout A s endl: virtual -AO {} class В { M m: public: BCconst strings s) : mCin B ) { cout B s endl; virtual -BO {} public: E(const strings s) : ACfrom E ). BCfrom E ). CCfrom E ). mCin E ) { cout E s endl: class F : virtual public B. virtual public C, public D { M m: public: F(const strings s) : BCfrom F ). CCfrom F ), DCfrom F ). mCin F ) { cout F s endl: class G : public E. public F { M m: public: G(const strings s) : BCfrom G ). CCfrom G ). ECfrom G ). FCfrom G ). mCin G ) { cout G s endl: int mainO { G gCfrom main ): } III:- Отношения между классами из этого примера представлены на следующей диаграмме: Каждый класс содержит вложенный объект типа М. Отметьте, что виртуальными являются лишь четыре наследования: Е от В и С, а также F от В и С. Результат выполнения программы выглядит так: М in В В from G М in С С from G М in А А from Е
|
© 2006 - 2024 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки. |