HDU 5001 Walk
解题思路:这是一道简单的概率dp,只要处理好相关的细节就可以了。
dp[d][i]表示走d步时走到i的改概率,具体参考代码:
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #include<vector> 5 #include<cstring> 6 using namespace std; 7 const int N = 10005; 8 const int M = 55; 9 double dp[N][M]; 10 int n, m, t, d; 11 vector<int> v[M]; //vector表示不定长数组 12 13 double solve(int x) 14 { 15 double ans = 0; 16 memset(dp, 0, sizeof(dp)); 17 for(int i = 1; i <= n; i++) dp[0][i] = 1.0/n;// 表示还没走时,走到每个点的概率 18 for(int i = 0; i < d; i++) 19 { 20 for(int j = 1; j <= n; j++) 21 { 22 if(j == x) continue; //不会走到与自己相同的点上 23 int s = v[j].size(); //与点j相连的数有多少个 24 for(int k = 0; k < s; k++) 25 { 26 int c = v[j][k]; //与j相连的第k个数 27 dp[i+1][c] += dp[i][j]*1.0/s; //这里很难给你讲清楚,自己好好思考 28 //心中有个具体的场景就更好 29 } 30 } 31 } 32 for(int i = 1; i <= n; i++) 33 { 34 if(i == x) continue; 35 ans += dp[d][i]; //第d步到其它所有点的概率之和为 36 //第d步没走到第x点的概率。 37 } 38 return ans; 39 } 40 41 int main() 42 { 43 int a, b; 44 scanf("%d", &t); 45 while(t--) 46 { 47 scanf("%d %d %d", &n, &m, &d); 48 for(int i = 1; i <= n; i++) v[i].clear(); 49 while(m--) 50 { 51 scanf("%d %d", &a, &b); 52 v[a].push_back(b); //向尾部添加元素,关于vector的用法,自己参考资料 53 v[b].push_back(a); 54 } 55 for(int i = 1; i <= n; i++) printf("%.10lf\n", solve(i)); 56 } 57 return 0; 58 }