您的位置:首页 > 其它

Chapter 4 | Trees and Graphs--判断有向图两节点之间是否存在路径

2014-07-24 15:10 351 查看
4.2  Given a directed graph, design an algorithm to find out whether thereis a route between two nodes.

译文:给定一个有向图,设计一个算法判断两节点之间是否存在路径。

这个题目实际上就是考察图的遍历,前面已经介绍了图的两种遍历方式:BFS和DFS 。这里判断两个节点之间是否存在路径,实质就是给定一个开始顶点,然后判断能否遍历到另一个指定顶点。这种情况下,我们采用BFS遍历判断。

先构建一个有向图(前面我们构建的都是无向图)

                                    




#include <iostream>
#include <list>

using namespace std;

class graph
{
public:
graph(int v) :vertex(v){
adj = new list<int>[v];
}

void addEdge(int v, int w);
bool BFS(int vStart, int vEnd);

private:
int vertex;
list<int> *adj;
};

//v:边的首顶点;w:边的尾顶点
void graph::addEdge(int v, int w)
{
adj[v].push_back(w);
}
构建有向图:

int main()
{
    graph g(4);
    g.addEdge(0, 1);//注释该行,构建的有向图如第二图所示
    g.addEdge(0, 2);
    g.addEdge(1, 2);
    g.addEdge(2, 0);
    g.addEdge(2, 3);
    g.addEdge(3, 3);

    if (g.BFS(2, 1))
        cout << "yes" << endl;
    else
        cout << "no" << endl;

    return 0;
}BFS
bool graph::BFS(int vStart, int vEnd)
{
bool *visited = new bool[vertex];
memset(visited, false, vertex);

list<int> queue;//利用链表构建一个队列

visited[vStart] = true;//表示开始访问
queue.push_back(vStart);//开始顶点入队

list<int>::iterator iter;

//队列中的顶点就是访问的顶点
while (!queue.empty())
{
vStart = queue.front();//这里有个优先级,邻接表中链表的头节点优先级最高,依次降低
queue.pop_front();//已访问顶点出队

if (vStart == vEnd)//如果已访问的顶点恰好是指定目的顶点则表明有路径
return true;

//将与开始顶点最近的顶点,也就是链表中的顶点依次入队
for (iter = adj[vStart].begin(); iter != adj[vStart].end(); ++iter)
{
if (!visited[*iter])
{
visited[*iter] = true;//标记即将访问,事实上,进入队列了就是要访问的
queue.push_back(*iter);//从链表头节点到尾节点依次入队
}
}
}
return false;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息