经常我会遇到类似的代码
/*initializer list of some class*/:m_member(some_param,/* --> */ *this)
Run Code Online (Sandbox Code Playgroud)
这样做的原因是m_member可以从包含它的类中调用成员函数... aka
//code in class that is m_member instance of
m_parent->some_function();
Run Code Online (Sandbox Code Playgroud)
我个人不喜欢它,因为我认为它是可怜的设计("亲爱的孩子,你知道你在做什么对你的课程封装"),但我想知道一般这种行为不好,如果是这样,如何避免这种设计.
编辑:请不要把重点放在initalizer列表中,让我们说它是在ctor体内.
这可能是灾难性的,因为您的父级不是在参考集的时间构建的。以下示例将演示这一点:
#include <iostream>
using namespace std;
struct TheParent;
struct TheChild
{
TheChild(TheParent& parent);
TheParent& myParent;
};
struct TheParent
{
TheParent()
: mychild(*this)
, value(1)
{
cout << "TheParent::TheParent() : " << value << endl;
}
TheChild mychild;
int value;
};
TheChild::TheChild(TheParent& parent)
: myParent(parent)
{
cout << "TheChild::TheChild() : " << myParent.value << endl;
};
int main()
{
TheParent parent;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
产生以下输出,清楚地注意到父对象的不确定状态:
TheChild::TheChild() : 1606422622
TheParent::TheParent() : 1
Run Code Online (Sandbox Code Playgroud)
底线:不要这样做。您最好使用动态子分配,但即使这样也有警告:
#include <iostream>
using namespace std;
struct TheParent;
struct TheChild
{
TheChild(TheParent& parent);
TheParent& myParent;
};
struct TheParent
{
TheParent()
: mychild(NULL)
, value(1)
{
mychild = new TheChild(*this);
cout << "TheParent::TheParent() : " << value << endl;
}
~TheParent()
{
delete mychild;
}
TheChild* mychild;
int value;
};
TheChild::TheChild(TheParent& parent)
: myParent(parent)
{
cout << "TheChild::TheChild() : " << myParent.value << endl;
};
int main()
{
TheParent parent;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
这给了你你可能希望得到的:
TheChild::TheChild() : 1
TheParent::TheParent() : 1
Run Code Online (Sandbox Code Playgroud)
但请注意,如果它TheParent是继承链中的中间类,并且您希望访问尚未构造的派生类中函数的可能被重写的虚拟实现,那么即使这样也会存在问题。
再说一次,最重要的是,如果您发现自己这样做,您可能首先要考虑一下为什么需要这样做。
| 归档时间: |
|
| 查看次数: |
156 次 |
| 最近记录: |