1.波那契堆(Fibonacci Heap) 斐波那契堆是一种松散的二项堆,与二项堆的主要区别在于构成斐波那契堆得树可以不是二项树,并且这些树的根排列是无须的(二项堆的根结点排序是按照结点个数排序的,不是按照根结点的大小)。斐波那契堆得优势在于它对建堆、插入、抽取最小关键字、联合等操作能在O(1)的时间内完成(不涉及删除元素的操作仅需要O(1))。这是对二项堆效率的巨大改善。但由于斐波那契堆得常数因子以及程序设计上的复杂度,使它不如通常的二叉堆合适。因此,它的价值仅存在于理论意义上。斐波那契堆的另一个特点就是合并操作只发生在抽取一个结点之后,也就是说斐波那契堆的维护总是会延后的。
结点结构:
key: 关键字,作为排序、判断结点大小的标准
left, right:用于维护双链表,所有的根结点形成一个双链表,每个结点的孩子们形成双链表
parent, child : 维护父子关系
mark : 这个域与维护堆结构无关,只与具体的算法策略有关,不在这里讲
degree: 记录该结点有几个孩子
每个结点x的域
- 父节点p[x]
- 指向任一子女的指针child[x]——结点x的子女被链接成一个环形双链表,称为x的子女表
- 左兄弟left[x]
- 右兄弟right[x]——当left[x] = right[x] = x时,说明x是独子。
- 子女的个数degree[x]
- 布尔值域mark[x]——标记是否失去了一个孩子
---------------------------------------------------------------------我是分割线-------------------------------------------------------------
对一个有向无环图(Directed Acyclic Graph简称DAG)G进行拓扑排序,是将G中所有顶点排成一个线性序列,使得图中任意一对顶点u和v,若边(u,v)∈E(G),则u在线性序列中出现在v之前。通常,这样的线性序列称为满足拓扑次序(Topological Order)的序列,简称拓扑序列。简单的说,由某个集合上的一个偏序得到该集合上的一个全序,这个操作称之为拓扑排序。
如果图中任意两点都是连通的,那么图被称作连通图。如果此图是有向图,则称为强连通图(注意:需要双向都有路径)。
在无向图中,如果从顶点vi到顶点vj有路径,则称vi和vj连通。如果图中任意两个顶点之间都连通,则称该图为连通图,否则,称该图为非连通图,则其中的极大连通子图称为连通分量,这里所谓的极大是指子图中包含的顶点个数极大。
一个有向图的极小连通子图是生成森林由若干棵有向树组成,含有图中全部顶点,但只有足以构成若干棵步相交的有向树的弧。
极小连通子图 = 该图的生成树
极大连通子图 = 该生成树加上其节点间直接相连的全部边
-----------------------------------------------------------------我是分割线-------------------------------------------------------------------------------------
欧拉回路:
有向强连通图中通过图G中每一条边仅一次,但是每一个顶点可以多次的回路。
挂接点:连通图中的关键节点
桥:连通图中的关建边
[双连通图、割点与桥]
如果一个无向连通图的点连通度大于1,则称该图是点双连通的(point biconnected),简称双连通或重连通。一个图有割点,当且仅当这个图的点连通度为1,则割点集合的唯一元素被称为割点(cut point),又叫关节点(articulation point)。
如果一个无向连通图的边连通度大于1,则称该图是边双连通的(edge biconnected),简称双连通或重连通。一个图有桥,当且仅当这个图的边连通度为1,则割边集合的唯一元素被称为桥(bridge),又叫关节边(articulation edge)。
可以看出,点双连通与边双连通都可以简称为双连通,[双连通分支]
在图G的所有子图G'中,如果G'是双连通的,则称G'为双连通子图。如果一个双连通子图G'它不是任何一个双连通子图的真子集,则G'为极大双连通子图。双连通分支(biconnected component),或重连通分支,就是图的极大双连通子图。特殊的,点双连通分支又叫做块。
【不妨害边 轻边】
【安全边规则】
【prim算法】
注意:区别是克鲁斯卡尔算法采用多个割来找安全边,而prim算法只有一个最大的割,来找安全边。
----------------------------------------------------------我是分割线------------------------------------------------------------------
Dijkstra算法无法判断含负权边的图的最短路。如果遇到负权,在没有负权回路存在时(负权回路的含义是,回路的权值和为负。)即便有负权的边,也可以采用Bellman-Ford算法正确求出最短路径。
【Bellman-Ford算法】--------单源
松弛操作:检查距离是否可以更新。
-----------------------------------------------------------------我是分割线--------------------------------------
【 SPFA算法原理】-------------------多个源,图中任意点
动态逼近法:设立一个先进先出的队列用来保存待优化的结点,优化时每次取出队首结点u,并且用u点当前的最短路径估计值对离开u点所指向的结点v进行松弛操作,如果v点的最短路径估计值有所调整,且v点不在当前的队列中,就将v点放入队尾。这样不断从队列中取出结点来进行松弛操作,直至队列空为止。