最短路+网络流算是很经典的套路了。
但是自己还是一直WA得不明所以。
原因是自己对edmondskarp算法的不理解。
首先,这道题的图是无向图,这点从题干中可以很容易的得到。
跑完Dijkstra后,我们得到了一个最短路树。
最早听说最短路树的概念是在大白书P330上。
意思是Dijkstra算法跑完以后会得到一个p数组,表示s到v的最短路径中v的前一个节点。
显然p数组能表示一个以s为根的树,如果想要从原点出发沿着最短路走到任意其他点,只要顺着树上的边走即可。
但是,最短路不唯一,最短路树对每一个节点只标出了一个最短路,如果非要标记出所有最短路的话,树形结构肯定是不够用的。
事实上,对于没有负环的图,所有可能的最短路会形成一个有向无环图。
我们也不需要弄一个什么结构去记录它,d数组就是一个最好的记录。
我们只需要沿着d[e.to]==d[e.from]+e.dist的方向走就ok了。
虽然有时候会走到死胡同,从而导致多了一些不必要的搜索,但是这不会慢太多,而且也没什么更简单实用的方法了。
我们就利用d数组的记录去建立一个网络流,网络流的边是有向边,每个有向边都有一个正向弧和一个反向弧。反向弧是为了反向增广,这和再加一条反向的有向边是不一样的。
我们应该利用最短路的有向无环图去建立一个有向网络流。如果建成无向网络流那就错了。
总结一下:
1、对原图建立无向图。
2、对原图跑Dijkstra得到最短路的有向无环图。
3、在这个有向无环图上跑bfs得到通过边数最少的最短路。
4、对这个有向无环图建立有向网络流,跑