在本代码实现使用广度优先搜索算法实现遍历无向图。本代码中不建立广度搜索树。
保存无向图的文件名是MapInfo.txt,里面存储着无向图的邻接矩阵,内容如下:
0 1 0 0 1 0 0 0
1 0 0 0 0 1 0 0
0 0 0 1 0 1 1 0
0 0 1 0 0 0 1 1
1 0 0 0 0 0 0 0
0 1 1 0 0 0 1 0
0 0 1 1 0 1 0 1
0 0 0 1 0 0 1 0
在本代码中使用队列来给每个节点设定“优先级”,即遍历的先后次序。代码如下:
#include <iostream>
#include <stdlib.h>
#include <stdio.h>
#define MAX 10000
enum {White,Grey,Black};
typedef struct MapNode
{
int NodeName;
int deep;
int color;
struct MapNode* next;
} MapNode;
typedef struct Queue
{
MapNode *node;
struct Queue *next;
} thisQueue;
MapNode *Head[8];
thisQueue *QueueHead = (thisQueue *)malloc(sizeof(thisQueue));
static int EnQueue(thisQueue *);
static thisQueue* DeQueue(void);
static bool QueueIsEmpty(void);
static void GetMapInfo(void);
static void InitHead(void);
static void InsertToNeiborTable(MapNode *, MapNode *);
static void Breadth_First_Search(MapNode*);
void ColorAll(int NodeName, int color)
{
for(int i=0;i<8;i++)
{
MapNode *p = Head[i];
while(p!=NULL)
{
if(p->NodeName == NodeName)
{
p->color = color;
}
p = p->next;
}
}
}
void Breadth_First_Search(MapNode *root)
{
root->color = Grey;
root->deep = 0;
std::cout << root->NodeName << " deep:"<<root->deep<<std::endl;
ColorAll(root->NodeName,Grey);
thisQueue *qu = (thisQueue *)malloc(sizeof(thisQueue));
qu->node = root;
qu->next = NULL;
EnQueue(qu);
while(!QueueIsEmpty())
{
thisQueue* dqu = DeQueue();
MapNode *p = dqu->node;
MapNode *p1 = p;
while(p != NULL)
{
if(p->color == White)
{
p->color = Grey;
p->deep = (p1->deep) + 1;
std::cout << p->NodeName << " deep:"<<p->deep<<std::endl;
thisQueue *newQue = (thisQueue *)malloc(sizeof(thisQueue));
for(int i=0;i<8;i++)
{
if(Head[i]->NodeName == p->NodeName)
{
newQue->node = Head[i];
Head[i]->color = p->color;
ColorAll(Head[i]->NodeName,Grey);
Head[i]->deep = p->deep;
break;
}
}
//newQue->node = p;
newQue->next = NULL;
EnQueue(newQue);
}
p = p->next;
}
p1->color = Black;
ColorAll(p1->NodeName,Black);
}
}
thisQueue *DeQueue(void)
{
if(QueueIsEmpty()) return NULL;
thisQueue *p = QueueHead;
QueueHead = QueueHead->next;
return p;
}
bool QueueIsEmpty(void)
{
if(QueueHead == NULL) return true;
else return false;
}
int EnQueue(thisQueue *node)
{
int count = 1;
if(QueueHead == NULL)
{
QueueHead = node;
return 1;
}
thisQueue *p = QueueHead;
while(p->next != NULL)
{
count++;
p = p->next;
}
p->next = node;
count++;
return count;
}
void InitHead(void)
{
for(int i=0;i<8;i++)
{
Head[i] = (MapNode *)malloc(sizeof(MapNode));
Head[i]->NodeName = i+1;
Head[i]->deep = MAX;
Head[i]->color = White;
Head[i]->next = NULL;
}
QueueHead = NULL;
}
void InsertToNeiborTable(MapNode *head,MapNode *node)
{
MapNode *p = head;
while(p->next != NULL) p = p->next;
p->next = node;
}
void InitMapInfo(void)
{
FILE *fp = fopen("MapInfo.txt","rb");
if(!fp)
{
std::cout << "Open MapInfo.txt failed!" << std::endl;
return ;
}
int Relation[8] = {0};
int index = 0;
int i = 0;
int n = 0;
while(1)
{
n = fscanf(fp,"%d %d %d %d %d %d %d %d",&Relation[0],&Relation[1],&Relation[2],&Relation[3],&Relation[4],&Relation[5],&Relation[6],&Relation[7]);
if(n < 1) break;
for(i=0;i<8;i++)
{
if(Relation[i] == 1)
{
MapNode *node = (MapNode *)malloc(sizeof(MapNode));
node->NodeName = i+1;
node->deep = MAX;
node->color = White;
node->next = NULL;
InsertToNeiborTable(Head[index],node);
}
}
index++;
}
fclose(fp);
fp = NULL;
}
int main()
{
InitHead();
QueueHead = NULL;
InitMapInfo();
Breadth_First_Search(Head[0]);
//std::cout << std::endl;
return 0;
}
当然,本代码的方法肯定比不上创建广度搜索树,仅从内存使用上来看,本程序会占用更大的内存。但对学习广度优先搜索也能提供参考价值