最小树形图 && LCA && Tarjan && 最/次短路

来源:互联网 发布:淘宝店铺付费引流 编辑:程序博客网 时间:2024/06/05 04:01

最小树形图 && LCA && Tarjan && 最/次短路

一、最小树形图

定义:选择一些边,使得根节点能够到达图中所有的节点,并使得选出的边的边权和最小。
(其实就是有向图的最小生成树)
算法:类似于最小生成树,朱刘算法:
1、 判断图是否连通(。。。)
2、 除了根节点,给每个节点找到一个连入的权值最小的边,用数组记录,pre[i]为前驱,f[i]为边权。
(此时将所有选的权值加起来,为tmp)
3、 在选的所有边中,如果并不构成环,则直接输出tmp即可
4、 如果有环,则对环进行缩点:
假设环上有点a[1],a[2],a[3],•••,a[n],缩成的点为b,对于所有不在环上的点c:
(1) c到b的距离为min{e[c,a[i]]-f[a[i]]};
(2)b到c的距离为min{e[a[i],c]};
5、 至此,过程结束
例题:hdu 4966
将每门课的等级拆开,等级i向等级i-1连接一条权值为0的边,表示我们如果学会了这个等级的技能,上一等级也就学会了。
然后每个a l1向b l2连接一条权值为w的有向边,表示花费w学会这个技能。
跑一边最小树形图即可。

二、LCA

定义:两点的最近公共祖先
算法:tarjan / 倍增 / 链剖
这里主要叙述 Tarjan(离线)
1、 任选一个点为根结点并开始操作
2、 遍历该节点的所有子节点,并标记为访问过。
3、 如果子节点还有子节点,则继续第二步。
4、 将子节点合并到父节点上
5、 然后继续寻找与当前点a有询问关系的结点b
6、 如果b已经被访问过了,则b和a的lca为b所被合并到的点c
例题:cdoj 92
如果加上某条边,你就只有三种走的方式。
要么就和原来一样,要么就是u-A-B-v,要么就是u-B-A-v。
然后跑lca就行了

三、Tarjan

口胡:Tarjan算法用来处理强联通分量问题。例如有向图的连通性,无向图的割点和割边问题
算法
1、每次选择一个点,压入栈中
2、使用dfn记录时间戳,用low记录该点能访问到的所有点。
3、每有一个dfn=low的点,就将栈顶直到当前点的所有点都弹出,这些点构成了一个联通分量。
例题:poj 1144
其实就是一个无向图求割点。(然而说到这里还是不会。。。)
无向图求割点可以使用tarjan。 (!!!)
对每个点依然用正常方式跑tarjan,与有向图缩点不同,如果访问到的点可以访问到dfn值更小的点,这说明儿子节点和上面的点形成了环,这个点不是割点。
如果有一个儿子不满足以上条件,就说明形成了割点

四、最、次短路

算法:最短路:spfa / dijkstra,不再叙述
次短路:两种记录方式。
第一种是在更新的时候记录一下,当前最短变次短,同样也可以记录路径数量。(麻烦一点)
第二种就是还正常跑最短路,记录每个点到起点和终点的最短距离,然后枚举每一条边,
查看到两端距离即可。不过这种方法不能记录路径数量。
例题:无

阅读全文
0 0
原创粉丝点击