图结构(Graph)

   定义:图可以理解由顶点集合V和边的集合E构成的一种数据结构
G=(V,E)。图的边可用括号括住两个顶点来表示,通常用圆括号
表示无向图的边,尖括号表示有向图的边。

    定义:与一个顶点有关的边的个数称为该顶点的度。对有向图的顶点
的度可进一步分为出度+入度,出度是指从该顶点出发的边数,入度是
指到达该顶点的边数。

    定义:路径中包含边的个数称为路径长度。

    定义:对于一个图,从Vi顶点出发有路径可达顶点Vj,则称顶点
Vi,Vj连通。对无向图,如果任何两个不同的顶点都连通,称为连通
图。对于有向图,如果任何两个顶点都连通则称为强连通图。

    定义:对于一个图如果对边赋以权值,则称这种边带权的图为网络。
在实际问题中边的权可理解为距离、代价、费用等。

    定义:若一个图的顶点和边都是另一个图的顶点和边的子集,也就是
说G2实际是G1的一部分,则称G2是G1的子图。

    图的存储结构:通常采用邻接矩阵表示顶点之间的关联,这种方法属
静态分配内存;另一种分配存储的方式是通过链式结构表示与顶点关联
的边表,这种方式称为邻接表。


定义图:1邻接矩阵表示
    矩阵的[i,j]元素为1表示(Vi,Vj)边存在,为0表示(Vi,Vj)边不存在。
CONST n=<MAXgNum>;
TYPE  adj=0..1;
      adjm=array[1..n,1..n] of adj;{邻接矩阵}
      graph=RECORD
            V:array[1..n] of Vtype;{顶点元素}
            E:adjm;
            END;
    邻接矩阵同样可以表示网络,对于网络可以直接在边的位置上填上权值,没有边的位
置可以认为权值为0或一个不可能的很大值MAX,为了简化表示可写为M。
        2用邻接表表示
    用邻接表表示图的结构,实际上邻接表由两个部分组成,一个是存储顶点数据元素的
顶点表,另一个是与顶点相关联的边表,对有向图边表还要再分为入边表和出边表。
TYPE Epinter=^enode;        {指向边表结点}
     enode=RECORD           {边表数据元素}
           adjv:1..n;       {顶点在顶点表中的位置}
           next:epinter;    {链接用指针}
           END;
     Vnode=RECORD           {顶点表数据元素}
           V:Vtype;         {顶点数据}
           LINK:Epinter;
           END;
     adjl=ARRAY[1..N] OF Vnode;
建立无向图结构的邻接表算法:
Procedure SCLJB(Var T:adjl);{生成无向图邻接表}
Begin
    for i:=1 to n do        {建立顶点表}
        read(T[i],V);
        T[i].link:=NIL;
    end for;
    for k:=1 to e do        {E为边数}
        read(i,j);          {读入边(Vi,Vj)}
        new(s);             {分配表边元素,S为Epinter类型}
        s^.adjv:=j;
        s^.next:=T[i].link;
        T[i].link:=s;       {顶点j作为Vi的边表元素}
        new(s);             {分配邻接于Vj的边表元素}
        s^.adjv:=i;
        s^.next:=T[j].link;
        T[j].link:=s;       {顶点i作为Vj的边表元素}
    end for;
End;
对连通图顶点的遍历算法:
    1连通图的深度优先遍历算法
Procedure DFS(i:1..n);         {从Vi开始深度优先遍历}
Begin{设Vflag--标记顶点的数组--和邻接表T调用时已知}
    write(T[i].V);             {访问Vi}
    Vflag[i]:=true;
    p:=T[i].link;              {沿边表向前一步}
    while p<>NIL do            {边表不完继续深度优先搜索遍历}
        if not Vflag[p^.adjv]  {边表找到的顶点没有访问过}
             then DFS(p^.adjv);{对找到的顶点继续深度优先遍历}
        end if;
        p:=p^.next;            {沿Vi的边表前进一步}
    end while;
End;
    2连通图的广度优先遍历算法
Procedure BFS(i:1..n);
Begin
    NULL(Q);       {队列Q初始化,用于保存优先搜索边表中顶点的序号}
    Write(T[i].V);         {访问Vi}
    Vflag[i]:=true;        {置Vi的访问标记}
    ENQU(Q,i);             {Vi进队列}
    while not EMPTY(Q) do  {队列不空进BFS}
        i:=DEQU(Q);        {从队列取顶点}
        p:=T[i].link;      {取边表指针}
        while p<>NIL do    {沿边表涉及顶点搜索}
            if not Vflag[p^.adjv]     {边表涉及顶点未被访问过}
               then
               write(T[p^.adjv].V);
               Vflag[p^.adjv]:=true;
               ENQU(Q.p^.adjv);       {访问的顶点进队列}
            end if;
        p:=p^.next;        {在边表中取下一个邻接边}
        end while;
    end while;
End;

转载于:https://my.oschina.net/RapidBird/blog/3402

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值