首先,我们可以得出一个结论:
- 令点 \(i,j\) 之间的最短路径边权和 \(dis_{i,j}\),若存在一个点 \(k\),使得 \(k \neq i\) 且 \(k \neq j\) 且 \(dis_{i,k}+dis_{k,j}=dis_{i,j}\),则连接 \(i,j\) 的边可以被删去。
该结论的正确性是显然的,因为将连接 \(i,j\) 的边删去后,\(i,j\) 之间的最短路径可以被 \(i,k + k,j\) 之间的最短路径所代替。
于是我们先使用 floyd 算法跑一遍最短路,求出 \(dis\) 数组;
然后枚举每条边,若该边满足上述结论,就令答案累加即可。
时间复杂度 \(O(n^3+m)\)。
核心代码:
for(int i=1;i<=m;i++)
for(int j=1;j<=n;j++)
if(j!=G[i].u&&j!=G[i].v&&dis[G[i].u][j]+dis[j][G[i].v]==dis[G[i].u][G[i].v]){
ans++; break;
}