![](/img/trans.png)
[英]For { A=a; B=b; }, will “A=a” be strictly executed before “B=b”?
[英]A -> B, B -> A classes association
这段代码没有做任何特别的事情。 这只是用前向声明显示问题的摘要。 只是一个简短的问题:为什么它不起作用以及如何强制它起作用?
class A;
class B {
A obj;
public:
int getB() const {
return 0;
}
void doSmth() {
int a = obj.getA();
}
};
class A {
B obj;
public:
int getA() const {
return 1;
}
void doSomething() {
int b = obj.getB();
}
};
这段代码给了我错误:
error C2079: 'B::obj' uses undefined class 'A'
error C2228: left of '.getA' must have class/struct/union
前向声明仅允许您使用对象的指针和引用。 您试图在提供类定义之前完全定义一个。
要使此工作有效,应将A中的obj更改为指针(可能不是最佳解决方案)或使用PIMPL惯用语(对它进行谷歌搜索),这样就可以解决此问题。
您的构造根本没有意义。 A
或B
都不是定义明确的结构,因为它们包含无限递归的子对象序列。
您刚刚提供了一个与此问题相同的稍微模糊的示例:
struct Box { Box hubert; };
同样,此数据结构没有任何意义。
如果可以的话,编程中的所有内容都必须有限且有充分的基础。
实际上,C ++要求类定义必须只包含具有完整类型的成员对象,从而禁止您尝试执行操作。 但这归结为合乎逻辑。 只要考虑一下如何初始化这样的数据结构。 总是必须先有事情 。
这种循环依赖类型在C ++中是不可能的。 您不能有彼此包含的对象。 但是,您可以存储指针或引用。 没有完整的定义,您也不能真正使用类的方法。
因此,您需要做两件事:
1)用指针替换对象。
2)在类定义之后实施方法。 如果它们在标题中,则需要将它们标记为inline
以防止多个定义。
class A;
class B {
std::shared_ptr<A> obj;
public:
int getB() const;
void doSmth();
};
class A {
std::shared_ptr<B> obj;
public:
int getA() const;
void doSomething();
};
inline int B::getB() const {
return 0;
}
inline void B::doSmth() {
int a = obj->getA();
}
inline int A::getA() const {
return 1;
}
inline void A::doSomething() {
int b = obj->getB();
}
我认为您需要为obj A和obj B创建头文件来解决您的问题。 当定义了B时,它仅知道A存在,而不知道A具有的功能/方法。
每个头文件都需要包含每个函数/方法的原型。 例:
class A{
int GetA() const;
void DoSomething();
}
该格式可能已关闭(我习惯了Obj C标头),但应该会有所帮助。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.