1. 程式人生 > >NOI2007 社交網絡

NOI2007 社交網絡

代碼 code https http mat 我們 思路 show names

傳送門


%%%\(\sf{ZYD\;\;TQL}\)


看數據範圍應該能想到\(floyd\)

第一步用\(floyd\)預處理出最短路,第二部比較難想(ZYD TQL),我們依舊可以用\(floyd\)來處理,第三步處理答案依舊可以用\(floyd\)……

個人感覺代碼比較好理解,但是思路真的不好想。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
long long int dis[110][110],vis[110][110];
double ans[110];
int read(){
    int k=0; char c=getchar();
    for(;c<'0'||c>'9';) c=getchar();
    for(;c>='0'&&c<='9';c=getchar())
      k=k*10+c-48;
    return k;
}
int main(){
    int n=read(),m=read();
    memset(dis,127/3,sizeof(dis));
    //for(int i=1;i<=n;i++) dis[i][i]=0;
    for(int i=1;i<=m;i++){
        int x=read(),y=read(),z=read();
        dis[x][y]=dis[y][x]=z;
        vis[x][y]=vis[y][x]=1;
    }
    for(int k=1;k<=n;k++)
      for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++){
            if(dis[i][j]>dis[i][k]+dis[k][j]){
                vis[i][j]=vis[i][k]*vis[k][j];
                dis[i][j]=dis[i][k]+dis[k][j];
            }
            else if(dis[i][j]==dis[i][k]+dis[k][j])
                vis[i][j]+=vis[i][k]*vis[k][j];
        }
    for(int k=1;k<=n;k++)
      for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++){
            if(i!=j&&j!=k&&dis[i][j]==dis[i][k]+dis[k][j])
                ans[k]+=(double)(vis[i][k]*vis[k][j])/(double)vis[i][j];
        }
    for(int i=1;i<=n;i++) printf("%.3lf\n",ans[i]);
    return 0;
}

NOI2007 社交網絡