Инициализация защищенных родительских элементов с помощью списка инициализации (C++)
можно ли использовать список инициализации конструктора дочернего класса для инициализации элементов данных, объявленных защищенными в родительском классе? Я не могу заставить его работать. Я могу обойти это, но было бы неплохо, если бы мне не пришлось.
пример кода:
class Parent
{
protected:
std::string something;
};
class Child : public Parent
{
private:
Child() : something("Hello, World!")
{
}
};
когда я пытаюсь это сделать, компилятор говорит мне:"класс 'Child' не имеет никакого поля с именем 'something'". Возможно ли что-то подобное? Если да, то каков синтаксис?
много спасибо!
4 ответа:
это невозможно в том виде, как вы описываете. Вам нужно будет добавить конструктор (может быть защищен) в базовый класс, чтобы переслать его вперед. Что-то вроде:
class Parent { protected: Parent( const std::string& something ) : something( something ) {} std::string something; } class Child : public Parent { private: Child() : Parent("Hello, World!") { } }
когда компилятор сталкивается со списком инициализаторов, объект производного класса еще не сформирован. Конструктор базового класса до сих пор не вызывался. Только после вызова конструктора базового класса,
somethingдоходит до того. Отсюда и проблема. Если вы не вызываете конструктор базового класса явно, компилятор делает это за вас (создавая соответствующий тривиальный конструктор для базового класса). Это вызываетsomethingэлемент для инициализации по умолчанию.из проекта C++0x:
12.6.2 инициализация баз и членов
2 имена в mem-инициализатор-id являются посмотрел в рамках класс конструктора и, если не найден в этой области находятся в область, содержащая конструктор определение. [ Примечание: если класс конструктора содержит член с таким же именем как сразу или виртуальный базовый класс класса, а mem-инициализатор-идентификатор именования элемента или базовый класс и состоит из одного идентификатор относится к члену класса. Meminitializer-id для скрытого базовый класс может быть задан с помощью уточненное имя. -конец Примечание ] если mem-инициализатор-id имена класс конструктора, нестатические данные член класса конструктора или прямая или виртуальная база этого класса, мем-инициализаторов-это плохо сформированные.
Примечание: Внимание шахта.
вы не могу инициализировать члены родительского класса в списке инициализации конструктора производного класса. Не имеет значения, защищены ли они, публичны или что-то еще.
в вашем примере, является членом
Parentкласс, что означает, что он может быть инициализирован только в списке инициализаторов конструктораParentкласса.