【发布时间】:2014-07-11 15:46:15
【问题描述】:
我正在用 C++ 编写自己的模板化 Graph 类的实现,因此我也在实现模板化 Vertex 和 Edge 类。因此,实现必须在它们各自的头文件中,而不是在单独的.cpp 文件中。 (最佳答案here 对我不起作用)
我的Vertex 类将出边的邻接列表存储为Edges 的vector,Edge 类存储指向源和目标Vertexs 的指针以及权重边缘。
由于Edge 只存储指向Vertex 的指针,因此在Edge.h 中转发声明Vertex 类就足够了。然后我可以在Vertex.h的顶部#include "Edge.h"。
这是解决 Vertex 和 Edge 类的相互依赖关系的最佳方法吗?用户必须#include 两个文件才能使用其中一个(即Graph.h)。
如果用户想要使用 Vertex 而不必明确包含 Edge.h 怎么办?反之亦然?我应该在另一个里面转发声明和#include吗?
或者我应该在同一个头文件中实现它们?
如果有的话,这个问题在 STL 中是如何解决的?
这是我现在拥有的:
Edge.h:
#ifndef _EDGE_H__
#define _EDGE_H__
template <class T> class Vertex;
template <class T>
class Edge
{
private:
Vertex<T>* _source;
Vertex<T>* _dest;
unsigned long long _weight;
...
};
#endif
顶点.h:
#ifndef _VERTEX_H__
#define _VERTEX_H__
#include "Edge.h"
#include <vector>
template <class T>
class Vertex
{
private:
std::vector<Edge<T> > _adj;
...
};
#endif
【问题讨论】:
-
我不确定让顶点拥有边缘是不是最好的设计。相反,我可能会同时拥有 Graph。
-
始终努力减少耦合。因为你已经成功了,你就完成了。虽然说如果你需要任何一个,你都需要两者是一个有效的论点,但将它们分开是太多的工作,没有任何收获......
-
另外,不要使用
_EDGE_H__等作为包含保护宏的名称。它们是保留的。 -
@T.C.你会推荐什么作为后卫?当 do this 而不是只说 *don't do this 时,它会更有用。
-
@localhost "使用not reserved的名称?
标签: c++ graph header-files circular-dependency