C++ 是否声明没有指针的默认参数循环引用?

C++ 是否声明没有指针的默认参数循环引用?,c++,header,definition,circular-reference,C++,Header,Definition,Circular Reference,有没有办法在头文件中声明这些类而无需间接寻址 // Forwards declaration of B class B; class A { public: // Default parameter referring to B. May return its parameter const B& func(const B& b = B()); }; class B { public: // B ctors B() {} B(cons

有没有办法在头文件中声明这些类而无需间接寻址

// Forwards declaration of B
class B;

class A
{
public:
    // Default parameter referring to B.  May return its parameter
    const B& func(const B& b = B());
};

class B
{
public:
    // B ctors
    B() {}
    B(const B&) {}

    // B has A as a member
    A a;
};

Visual C++ 2008用这个告诉我:

error C2514: 'B' : class has no constructors
并指向B的正向声明(“B类;”),显然看不到下面B的构造函数。A无法跟随B,因为B包含A作为成员


如果必须使用间接法,那么最好的方法是什么?也许在C++0x B中,A可以是唯一的\u ptr成员?或者可能有一个boost类纯粹是为了回避这个问题?

而不是默认参数声明两个重载,一个通过引用获取a
B
,另一个不获取参数。在不带参数的方法中,使用
B()
调用另一个方法,这将起作用,因为可以在定义
B
后定义该方法

...
    void func();
    void func(const B& b);
};

class B...

void A::func() { func(B()); }
void A::func(const B&) { }
更新:

func()返回常量B&

那可能不是个好主意。根据该定义,类似于:

const B& foo = a.func();
foo.bar();
将导致可怕的“未定义行为”(即崩溃),因为您引用的
B
将在第一条语句完成后立即销毁。通过引用返回类成员以外的内容通常是个坏主意

如果您真的想这样做,那么我认为您必须强制调用方显式地传入
B()
,即没有默认参数

a.func(B()).bar();
(这是使用此函数避免未定义行为的唯一方法。)

当然,你可以只返回一份副本而不是参考,但我想你有理由不这样做

根据您所做的工作,您可以使用智能指针(如
shared\u ptr
)而不是引用来设置更好的语义,这样您就可以有效地忽略对象的生命周期。然而,您必须开始注意引用循环


我不知道你想用它做什么,但你可能想看看一些,看看是否有一个既定的最佳实践。您可能会发现这个小问题是不幸选择了类结构或包含的征兆。

谢谢您的回答。这是可行的,但是我忘了提到-func()返回一个常量B&,并且可能返回它的参数,所以没有参数的版本没有意义。然后呢?