Действительно ли возможно передать - объявляют вложенный класс, затем используют его в качестве типа для бетона (не указатель на к) элемент данных внешнего класса?
Т.Е.
class Outer;
class Outer::MaybeThisWay // Error: Outer is undefined
{
};
class Outer
{
MaybeThisWay x;
class MaybeThatOtherWay;
MaybeThatOtherWay y; // Error: MaybeThatOtherWay is undefined
};
Вы не можете объявить вложенный класс таким образом.
В зависимости от того, что вы пытаетесь сделать, возможно, вы можете использовать пространство имен, а не класс на внешнем уровне. Вы можете объявить такой класс без проблем:
namespace Outer {
struct Inner;
};
Outer::Inner* sweets; // Outer::Inner is incomplete so
// I can only make a pointer to it
Если ваш Outer абсолютно точно должен быть классом, и вы не можете засунуть его в пространство имен, тогда вам нужно, чтобы Outer был полным типом в контексте, где вы объявляете Inner.
class Outer
{
class Inner; // Inner forward-declared
}; // Outer is fully-defined now
Outer yes; // Outer is complete, you can make instances of it
Outer::Inner* fun; // Inner is incomplete, you can only make
// pointers/references to it
class Outer::Inner
{
}; // now Inner is fully-defined too
Outer::Inner win; // Now I can make instances of Inner too
Нет, но что не так с
class Outer {
public: //or protected or private
class Inner {
};
private:
Inner foo;
};
Форвардное объявление здесь не имеет смысла, если только я чего-то не упускаю (что возможно, поскольку в вашем вопросе отсутствует много деталей)
Помните, если класс объявлен вперед, то вы можете объявлять только ссылки или указатели на объект объявленного вперед типа. Вы не можете делать с ним ничего другого, включая доступ к его членам или функциям.
Если класс был объявлен вперед (но у вас еще нет полного определения), вы можете объявить только указатель на него, потому что компилятор еще не знает размер класса (ни имена его полей или методов).
Невозможно перенаправить объявление вложенного класса без полного указания содержащего класса. Этот небольшой трюк как бы решает проблему
class Outer_Inner
{
};
class Outer
{
public:
typedef Outer_Inner Inner;
};
Это работает для меня, так как в моем соглашении об именах Outer_Inner
недопустимое имя класса, поэтому очевидно, что оно относится к вложенному классу.
Вы по-прежнему не можете напрямую объявить вложенный класс следующим образом:
class Outer::Inner;
Но, по крайней мере, он может быть объявлен вперед с помощью:
class Outer_Inner;
Если вам не нравится, как выглядит Outer_Inner, вы можете принять соглашение об именах для вложенных занятия, которые больше подходят вашему вкусу. Outer__Inner
, Outer_nested_Inner
и т. Д.
Если вы объявляете атрибут типа MaybeThatOtherWay
, не ссылка или указатель, компилятор должен знать полное определение класса, чтобы определить размер внешнего класса. Таким образом, вы не можете использовать предварительное объявление и такое объявление поля, будь то вложенный класс или нет.