У меня есть иерархия классов, которая сводится кVirtual Наследования с Конструктора Наследованием
class Module { };
struct Port {
Module& owner;
Port(Module& owner) : owner(owner) {}
};
struct InPort : virtual Port { using Port::Port; };
struct OutPort : virtual Port { using Port::Port; };
struct InOutPort : InPort, OutPort { using Port::Port; };
Как вы можете видеть, я бы предпочел, чтобы создать некоторую базовую функциональность, и наследовать его в классическом ромбе. Я также хотел бы использовать наследование конструктора, чтобы сделать его на будущее, как это возможно ...
Однако this does not work as written down above
prog.cpp: In function 'int main()':
prog.cpp:14:15: error: use of deleted function 'InOutPort::InOutPort(Module&)'
InOutPort p(m);
Даже замену определения InOutPort
с более явной версией is not enough:
struct InOutPort : InPort, OutPort { InOutPort(Module& m) : Port(m), InPort(m), OutPort(m) { } };
Вместо I seem to have to write down everything explicitly for it to work::
struct InPort : virtual Port { InPort(Module& m) : Port(m) { } };
struct OutPort : virtual Port { OutPort(Module& m) : Port(m) { } };
struct InOutPort : InPort, OutPort { InOutPort(Module& m) : Port(m), InPort(m), OutPort(m) { } };
Есть ли способ объединить наследование constuctor с виртуальным наследованием, которое я пропускаю?
Если нет, то какой вариант вы бы использовали?
Возможно, конструкторы шаблонов Variadic, которые отлично пересылают свои аргументы во все базы?
'InPort' и' OutPort' наследуют конструктор, который вызывает неразделенный конструктор по умолчанию для 'Port', потому что они оба не являются наиболее производными классами. Программа была бы плохо сформирована, если бы они были вызваны. Из-за этого gcc решает удалить соответствующие конструкторы в обоих классах. Clang не дает и не будет давать ошибок в конструкторах, даже если базы [явно инициализированы] (http://coliru.stacked-crooked.com/a/7c2963ba56e79793). Как и в стороне, clang также дает ошибку, потому что 'Port' не является прямым базовым классом' InOutPort' в объявлении использования, в то время как gcc игнорирует его. – 0x499602D2
GCC фактически удаляет конструкторы, потому что они будут плохо сформированы, но не по той причине, о которой я раньше догадывался. Кажется, что использование-декларация [неявно odr-использует конструктор по умолчанию] (http://coliru.stacked-crooked.com/a/490c0b5bb17fdc50). Конструктор по умолчанию в вашем классе 'Port' не объявлен, поэтому он удаляет вызывающий конструктор. Это ошибка. – 0x499602D2
Кроме того, это происходит только в том случае, если это виртуальный базовый класс. – 0x499602D2