C++ 两个成员相互依赖?

C++ 两个成员相互依赖?,c++,design-patterns,C++,Design Patterns,想象一下,有一个名为Node的类可以容纳多个父节点和多个子节点: class Node { public: Node(); virtual void addParent(Node *parent); virtual void addChild(Node *child); private: vector<Node*> m_parents; vector<Node*> m_chil

想象一下,有一个名为
Node
的类可以容纳多个父节点和多个子节点:

class Node {
    public:
        Node();
        virtual void addParent(Node *parent);
        virtual void addChild(Node *child);
    private:
        vector<Node*> m_parents;
        vector<Node*> m_children;
};
正如你所看到的,这不好。 我用四种方法来解决这个问题,而不是两种方法,但是感觉有点愚蠢。 另外两个方法都声明为
private
protected
,因此其他人无法调用它们。 下面是原始的
addParent
和一个名为
rawAddChild
的新方法:

void Node::addParent(Node *parent)
{
    if (m_parents.lacks(parent)) {
        m_parents.push_back(parent);
    }
    parent->rawAddChild(this);
}

void Node::rawAddChild(Node *child)
{
    if (m_children.lacks(child)) {
        m_children.push_back(child);
    }
    // Doesn't call for parent's method
}
这对于
addChild()
rawAddParent()
显然是相同的

然而,这并不是一个合适的解决方案,对于“局外人”来说,显然不清楚为什么会有
addChild
rawAddChild
方法。
我的逻辑有问题吗?如果有,我应该如何解决这个问题?或者我的解决方案已经很好了?

我建议只使用以下两种方法中的一种进行实际操作:

void Node::addParent(Node *parent)
{
    if (m_parents.lacks(parent)) {
        m_parents.push_back(parent);
    }
    if (parent->m_children.lacks(this)) {
        parent->m_children.push_back(this);
    }
}

void Node::addChild(Node *child)
{
    child->addParent(this);
}

我将测试向量是否已经包含元素(可能使用set而不是vector)


你应该抽象一点

bool Node::addParent(Node *parent)
{
    if (m_parents.lacks(parent)) { // supposing such method exists
        m_parents.push_back(parent);
        parent->updateRelationShip(parent,this);
        return true;
    }
    return false;
}

bool Node::addChild(Node *child)
{
    if (m_children.lacks(child)) {
        m_children.push_back(child);
        child->updateRelationShip(this,child); 
        return true;
    }
    return false;
}
void Node::updateRelationship(Node*parent, Node* child){
   parent->addChild(child);
   child->addParent(parent);
}

请注意,您甚至可以去掉几乎无用的方法,将代码留给一个方法而不是四个方法。求爱!我正要建议您的解决方案,但我注意到“addParent”和“addChild”是虚拟的。如果派生类在添加子类时有一些特殊行为,该怎么办?我建议对您的答案进行一个修改,即:使“addParent”和“addChild”非虚拟,如果需要,添加“onParentAdded”和“onChildAdded”派生类可以选择实现的虚拟方法。我假设
节点
不用于多态上下文,并且
虚拟
说明符不在这里是出于任何特定原因。请注意,我处于半睡眠状态,因此不完全确定是否存在循环引用,但您明白了。。。。
void Node::addParent(Node *parent)
{
    if (m_parents.lacks(parent)) { // supposing such method exists
        m_parents.push_back(parent);
    }
    if (parent->m_childs.find(this)==set::end)
        parent->addChild(this);
}

void Node::addChild(Node *child)
{
    if (m_children.lacks(child)) {
        m_children.push_back(child);
    }
    if (child->m_parents.find(this)==set::end)
        child->addParent(this);
}
bool Node::addParent(Node *parent)
{
    if (m_parents.lacks(parent)) { // supposing such method exists
        m_parents.push_back(parent);
        parent->updateRelationShip(parent,this);
        return true;
    }
    return false;
}

bool Node::addChild(Node *child)
{
    if (m_children.lacks(child)) {
        m_children.push_back(child);
        child->updateRelationShip(this,child); 
        return true;
    }
    return false;
}
void Node::updateRelationship(Node*parent, Node* child){
   parent->addChild(child);
   child->addParent(parent);
}