您的位置:首页 > 理论基础 > 数据结构算法

数据结构之图(存储结构、遍历)

2016-09-04 21:33 337 查看
一、图的存储结构

1.1 邻接矩阵

    图的邻接矩阵存储方式是用两个数组来表示图。一个一维数组存储图中顶点信息,一个二维数组(邻接矩阵)存储图中的边或弧的信息。

    设图G有n个顶点,则邻接矩阵是一个n*n的方阵,定义为:

    


    看一个实例,下图左就是一个无向图。

    


    从上面可以看出,无向图的边数组是一个对称矩阵。所谓对称矩阵就是n阶矩阵的元满足aij =
aji。即从矩阵的左上角到右下角的主对角线为轴,右上角的元和左下角相对应的元全都是相等的。

    从这个矩阵中,很容易知道图中的信息。

    (1)要判断任意两顶点是否有边无边就很容易了;

    (2)要知道某个顶点的度,其实就是这个顶点vi在邻接矩阵中第i行或(第i列)的元素之和;

    (3)求顶点vi的所有邻接点就是将矩阵中第i行元素扫描一遍,arc[i][j]为1就是邻接点;

    而有向图讲究入度和出度,顶点vi的入度为1,正好是第i列各数之和。顶点vi的出度为2,即第i行的各数之和。

    若图G是网图,有n个顶点,则邻接矩阵是一个n*n的方阵,定义为:

    


    这里的wij表示(vi,vj)上的权值。无穷大表示一个计算机允许的、大于所有边上权值的值,也就是一个不可能的极限值。下面左图就是一个有向网图,右图就是它的邻接矩阵。

    


    那么邻接矩阵是如何实现图的创建的呢?代码如下。

#include <iostream>

#define MAXVERTEX   10
#define INFINITY    255
#define DEBUG

#ifdef DEBUG
#define Debug_Code( code_fragment ) { code_fragment }
#else
#define Debug_Code( code_fragment )
#endif // DEBUG

typedef char VertexType;        //Define the type of the vertex
typedef int MatrixValue;        //Define the value int the edge Matrix

typedef struct tagGraph
{
VertexType vexs[MAXVERTEX];             //the array to store the vertexs.
MatrixValue arc[MAXVERTEX][MAXVERTEX];  //We use the two dim array to store the edge matrix.
int numVertexes;
int numEdges;
}Graph;

int locate(Graph * g, VertexType ch)
{
for(int i = 0; i < g->numVertexes; ++i)
{
if(g->vexs[i] == ch)
return i;
}
return -1;
}

bool CreateGraph(Graph * g)
{
std::cout << "Please input the number of Vertexes and the edges:" << std::endl;
std::cin >> g->numVertexes >> g->numEdges;

Debug_Code( std::cout << "The number of Vertex is " << g->numVertexes << std::endl
<< "The number of edges is " << g->numEdges << std::endl;
);

std::cout << "Please input the name of the vertexes standard as char type." << std::endl;

for(int i = 0; i < g->numVertexes; i++)
{
g->vexs[i] = getchar();
while(g->vexs[i] == '\n')
{
g->vexs[i] = getchar();
}
}

Debug_Code (
std::cout << "The vertex is: ";
for(int i = 0; i < g->numVertexes; i++)
std::cout << g->vexs[i] << " ";
std::cout << std::endl;
);

//Initialize the edge matrix
for(int i = 0; i < g->numEdges; i++)
for(int j = 0; j < g->numEdges; j++)
g->arc[i][j] = INFINITY;

//input the value for the edge matrix;
for(int i = 0; i < g->numEdges; i++)
{
VertexType p, q;
std::cout << "Please input the No." << i + 1
<< " edge  (vi,vj), and the value of the edge" << std::endl;
p = getchar();
while(p == '\n')
{
p = getchar();
}
q = getchar();
while(q == '\n')
{
q = getchar();
}
int value = 0;
std::cin >> value;

int m = -1, n = -1;
m = locate(g, p);
n = locate(g, q);
if(n == -1 || m == -1)
{
std::cout << " there is no this vertex." << std::endl;
return false;

}
g->arc[m]
= value;
g->arc
[m] = g->arc[m]
;
}
return true;
}

void printGraph(const Graph* g)
{

std::cout << "The structure of the graph is\n\t";
for(int i = 0; i < g->numVertexes; i++)
std::cout << g->vexs[i]<<"\t";
std::cout << std::endl;

for(int i = 0; i < g->numVertexes; i++)
{
std::cout << g->vexs[i] << "\t";
for(int j = 0; j < g->numVertexes; j++)
{
std::cout << g->arc[i][j] << "\t";

}
std::cout << std::endl;
}
}

int main()
{
//Test Case
Graph g;
CreateGraph(&g);
printGraph(&g);

return 0;
}


运行结果如下



 从代码中可以得到,n个顶点和e条边的无向网图的创建,时间复杂度为O(n + n2 +
e),其中对邻接矩阵Grc的初始化耗费了O(n2)的时间。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息