我正在尝试使用两个类实现类似树的结构:Tree
和Node
。问题是从每个类我想调用另一个类的函数,所以简单的前向声明是不够的。
让我们看一个例子:
tree.h中:
#ifndef TREE_20100118
#define TREE_20100118
#include <vector>
#include "Node.h"
class Tree
{
int counter_;
std::vector<Node> nodes_;
public:
Tree() : counter_(0) {}
void start() {
for (int i=0; i<3; ++i) {
Node node(this, i);
this->nodes_.push_back(node);
}
nodes_[0].hi(); // calling a function of Node
}
void incCnt() {
++counter_;
}
void decCnt() {
--counter_;
}
};
#endif /* TREE_20100118 */
Node.h:
#ifndef NODE_20100118
#define NODE_20100118
#include <iostream>
//#include "Tree.h"
class Tree; // compile error without this
class Node
{
Tree * tree_;
int id_;
public:
Node(Tree * tree, int id) : tree_(tree), id_(id)
{
// tree_->incCnt(); // trying to call a function of Tree
}
~Node() {
// tree_->decCnt(); // problem here and in the constructor
}
void hi() {
std::cout << "hi (" << id_ << ")" << endl;
}
};
#endif /* NODE_20100118 */
致电树
#include "Tree.h"
...
Tree t;
t.start();
这只是一个简单的例子来说明问题。所以我想要的是从Tree
对象调用Node
函数。
更新#1:感谢您的回答。我尝试像在Java中一样解决问题,即每个类只使用一个文件。我似乎必须开始分离.cpp和.h文件......
更新#2:下面,根据提示,我也粘贴了完整的解决方案。谢谢,问题解决了。
答案 0 :(得分:5)
在标题中,forward声明成员函数:
class Node
{
Tree * tree_;
int id_;
public:
Node(Tree * tree, int id);
~Node();
void hi();
};
在包含所有必需标头的单独.cpp文件中,定义它们:
#include "Tree.h"
#include "Node.h"
Node::Node(Tree * tree, int id) : tree_(tree), id_(id)
{
tree_->incCnt();
}
Node::~Node()
{
tree_->decCnt();
}
etc
这也可以保持标题的可读性,因此很容易看到类的界面一目了然。
答案 1 :(得分:2)
根据提示,这是完整的解决方案。
<强> tree.h中:强>
#ifndef TREE_20100118
#define TREE_20100118
#include "Node.h"
#include <vector>
class Tree
{
int counter_;
std::vector<Node> nodes_;
public:
Tree();
void start();
void incCnt();
void decCnt();
};
#endif /* TREE_20100118 */
<强> Tree.cpp:强>
#include "Tree.h"
#include "Node.h"
Tree::Tree() : counter_(0) {}
void Tree::start()
{
for (int i=0; i<3; ++i) {
Node node(this, i);
this->nodes_.push_back(node);
}
nodes_[0].hi(); // calling a function of Node
}
void Tree::incCnt() {
++counter_;
}
void Tree::decCnt() {
--counter_;
}
<强> Node.h:强>
#ifndef NODE_20100118
#define NODE_20100118
class Tree;
class Node
{
Tree * tree_;
int id_;
public:
Node(Tree * tree, int id);
~Node();
void hi();
};
#endif /* NODE_20100118 */
<强> Node.cpp:强>
#include "Node.h"
#include "Tree.h"
#include <iostream>
Node::Node(Tree * tree, int id) : tree_(tree), id_(id)
{
tree_->incCnt(); // calling a function of Tree
}
Node::~Node() {
tree_->decCnt();
}
void Node::hi() {
std::cout << "hi (" << id_ << ")" << std::endl;
}
答案 2 :(得分:1)
Tree
的定义需要Node
的定义,而不是相反,因此您的前瞻性声明是正确的。
您需要做的就是从Tree
类主体中删除需要Node
完整定义的任何函数的定义,并在.cpp
文件中实现完整定义两个班级都在范围内。
答案 3 :(得分:0)
你能在.cxx文件中构造函数/析构函数体吗?你可以在那里包含Tree.h。