1. 程式人生 > >PTA 7-12(圖) 社交網路圖中結點的“重要性”計算 最短路

PTA 7-12(圖) 社交網路圖中結點的“重要性”計算 最短路

7-12(圖) 社交網路圖中結點的“重要性”計算 (30 分)

在社交網路中,個人或單位(結點)之間通過某些關係(邊)聯絡起來。他們受到這些關係的影響,這種影響可以理解為網路中相互連線的結點之間蔓延的一種相互作用,可以增強也可以減弱。而結點根據其所處的位置不同,其在網路中體現的重要性也不盡相同。

“緊密度中心性”是用來衡量一個結點到達其它結點的“快慢”的指標,即一個有較高中心性的結點比有較低中心性的結點能夠更快地(平均意義下)到達網路中的其它結點,因而在該網路的傳播過程中有更重要的價值。在有N個結點的網路中,結點vi​​的“緊密度中心性”Cc(vi​​)數學上定義為vi​​到其餘所有結點vj​​ (ji) 的最短距離d(vi​​,vj​​)的平均值的倒數:

對於非連通圖,所有結點的緊密度中心性都是0。

給定一個無權的無向圖以及其中的一組結點,計算這組結點中每個結點的緊密度中心性。

輸入格式:

輸入第一行給出兩個正整數N和M,其中N(104​​)是圖中結點個數,順便假設結點從1到N編號;M(105​​)是邊的條數。隨後的M行中,每行給出一條邊的資訊,即該邊連線的兩個結點編號,中間用空格分隔。最後一行給出需要計算緊密度中心性的這組結點的個數K(100)以及K個結點編號,用空格分隔。

輸出格式:

按照Cc(i)=x.xx的格式輸出K個給定結點的緊密度中心性,每個輸出佔一行,結果保留到小數點後2位。

輸入樣例:

9 14
1 2
1 3
1 4
2 3
3 4
4 5
4 6
5 6
5 7
5 8
6 7
6 8
7 8
7 9
3 3 4 9

輸出樣例:

Cc(3)=0.47
Cc(4)=0.62
Cc(9)=0.35

思路:簡單的稀疏圖最短路問題,甚至不需要儲存邊權(均為一),dijkstra演算法裸過,讀入的時候判一下是不是連通圖

AC程式碼:

#include <iostream>
#include <cstring>
#include <algorithm>
#include 
<queue> #include <vector> #include <cstdio> #include <malloc.h> #define INF 0x3f3f3f3f #define FRER() freopen("in.txt", "r", stdin) #define FREW() freopen("out.txt", "w", stdout) using namespace std; const int maxn = 10000 + 5; vector<int> g[maxn]; int n, m, s, u, v, vis[maxn], dis[maxn]; typedef pair<int, int> P; void dijkstra() { memset(vis, 0, sizeof(vis)); memset(dis, INF, sizeof(dis)); priority_queue<P, vector<P>, greater<P> > q; dis[s] = 0; q.push(make_pair(0, s)); P tmp; while(!q.empty()) { tmp = q.top(); q.pop(); if(vis[tmp.second]) continue; vis[tmp.second] = 1; for(int i = 0; i < g[tmp.second].size(); ++i) { if(tmp.first + 1 < dis[g[tmp.second][i]]) { dis[g[tmp.second][i]] = tmp.first + 1; q.push(make_pair(dis[g[tmp.second][i]], g[tmp.second][i])); } } } } double cal() { double ans = 0; for(int i = 1; i <= n; ++i) ans += (double)dis[i]; return (n - 1) / ans; } int main() { scanf("%d %d", &n, &m); int num = 0; while(m--) { scanf("%d %d", &u, &v); g[u].push_back(v); g[v].push_back(u); if(!vis[u]) vis[u] = 1, ++num; if(!vis[v]) vis[v] = 1, ++num; } bool ok = !(num == n); scanf("%d", &m); while(m--) { scanf("%d", &s); if(ok) printf("Cc(%d)=0.00\n", s); else { dijkstra(); printf("Cc(%d)=%.2lf\n", s, cal()); } } return 0; }