Processing math: 100%

随笔 - 375  文章 - 2  评论 - 105  阅读 - 18万 

首先我们列出转移矩阵MMi,j=1pqdeg[i](i,j之间有边)or Mi,j=0(i,j之间没边)

则这个矩阵Mi,j表示的是站在某个点i,下一次走到j且没有爆炸的概率

我们再看Mni,j,表示的站在某个点i,走n步以后到达j且没有爆炸的概率

Mn的第一列代表了1号点到其他所有点的概率,设为列向量An,则An=MnB,其中B=(1,0,0,0,...)T

设第n步到各点且爆炸了的概率的列向量为Pn,则Pn=pqAn

故答案列向量Ans=+i=0Pi

把它展开:Ans=pq(+i=0Mi)B

由等比数列求和公式,+i=0Mi=IIM=(IM)1

Ans=pq(IM)1B,即(IM)Ans=pqB

得到一个线性方程组,我们只要高斯消元即可

 

复制代码
 1 /**************************************************************
 2     Problem: 1778
 3     User: rausen
 4     Language: C++
 5     Result: Accepted
 6     Time:200 ms
 7     Memory:2264 kb
 8 ****************************************************************/
 9  
10 #include <cstdio>
11 #include <cmath>
12 #include <algorithm>
13  
14 using namespace std;
15 typedef double lf;
16 const int N = 305;
17 const int M = N * N;
18  
19 inline int read();
20  
21 struct edge {
22     int next, to;
23     edge() {}
24     edge(int _n, int _t) : next(_n), to(_t) {}
25 } e[M];
26  
27 int n, m, deg[N];
28 int first[N], tot;
29 lf P, a[N][N], ans[N];
30  
31 inline void Add_Edges(int x, int y) {
32     e[++tot] = edge(first[x], y), first[x] = tot;
33     e[++tot] = edge(first[y], x), first[y] = tot;
34     ++deg[x], ++deg[y];
35 }
36  
37 #define y e[x].to
38 inline void build_matrix() {
39     int p, x;
40     for (p = 1; p <= n; ++p) {
41         for (x = first[p]; x; x = e[x].next)
42             a[p][y] = -(1.0 - P) / deg[y];
43         a[p][p] = 1;
44     }
45     a[1][n + 1] = P;
46 }
47 #undef y
48  
49 void gauss(int n) {
50     int i, j, k;
51     lf tmp;
52     for (i = 1; i <= n; ++i) {
53         for (k = i, j = i + 1; j <= n; ++j)
54             if (fabs(a[j][i]) > fabs(a[k][i])) k = j;
55         for (j = i; j <= n + 1; ++j) swap(a[i][j], a[k][j]);
56         for (k = i + 1; k <= n; ++k)
57             for (tmp = -a[k][i] / a[i][i], j = i; j <= n + 1; ++j)
58                 a[k][j] += a[i][j] * tmp;
59     }
60     for (i = n; i; --i) {
61         for (j = i + 1; j <= n; ++j)
62             a[i][n + 1] -= a[i][j] * ans[j];
63         ans[i] = a[i][n + 1] / a[i][i];
64     }
65 }
66  
67 int main() {
68     int i, j;
69     n = read(), m = read(), P = 1.0 * read() / read();
70     for (i = 1; i <= m; ++i)
71         Add_Edges(read(), read());
72     build_matrix();
73     gauss(n);
74     for (i = 1; i <= n; ++i)
75         printf("%.9lf\n", ans[i]);
76     return 0;
77 }
78  
79 inline int read() {
80     static int x;
81     static char ch;
82     x = 0, ch = getchar();
83     while (ch < '0' || '9' < ch)
84         ch = getchar();
85     while ('0' <= ch && ch <= '9') {
86         x = x * 10 + ch - '0';
87         ch = getchar();
88     }
89     return x;
90 }
View Code
复制代码

 

posted on   Xs酱~  阅读(426)  评论(0编辑  收藏  举报
点击右上角即可分享
微信分享提示