这到题要对floyd有一定理解才能做出,这也长了记性,算法还是要理解,知道其原理思想,
才能活学活用。如:这道题就揭视了floyd是根据动态规划得出的!!!
每当一个点x被mark的时候,对所有点对(i,j),更新cost[i][j] = min(cost[i][j], cost[i][x] + cost[x][j]),复杂度为O(N^2)。这种操作最多有N次,故总复杂度是O(N^3)
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
using namespace std;
//const int INF= 999999999;如果这里用此作为不联通的条件的化由于不知道范围很容易出错的!!!故改为了-1(由于没有负权)
int w[310][310];
int vis[310];
int n,m,Q;
void f(int u)
{
for(int i=0;i<n;i++)
for(int j=0;j<n;j++)
if(w[i][u]!=-1&&w[u][j]!=-1){
if(w[i][j]!=-1)
{
if(w[i][j]>w[i][u]+w[u][j])
w[i][j]=w[i][u]+w[u][j];
}
else w[i][j]=w[i][u]+w[u][j];
}
}
int main(){
int k=1;
while(scanf("%d%d%d",&n,&m,&Q)!=EOF){
if(n==0&&m==0&&Q==0) break;
memset(vis,0,sizeof(vis));
for(int i=0;i<n;i++) for(int j=0;j<n;j++) {if(i!=j) w[i][j]=-1;else w[i][j]=0;}
if(k>1) printf("/n");
printf("Case %d:/n",k);
int x,y,z;
for(int i=0;i<m;i++) { scanf("%d%d%d",&x,&y,&z); if(z<w[x][y]||w[x][y]==-1) w[x][y]=z; }
for(int i=1;i<=Q;i++){
scanf("%d",&x);
if(x==0){
scanf("%d",&z);
if(vis[z]) printf("ERROR! At point %d/n",z);
else {
vis[z]=1;
f(z);
}
}
else if(x==1){
scanf("%d%d",&y,&z);
if(!vis[y]||!vis[z]) printf("ERROR! At path %d to %d/n",y,z);
else{
int temp=w[y][z];
if(temp==-1) printf("No such path/n");
else printf("%d/n",temp);
}
}
}
k++;}
return 0;}