1. 程式人生 > >BZOJ1444: [Jsoi2009]有趣的遊戲(Trie圖,矩乘)

BZOJ1444: [Jsoi2009]有趣的遊戲(Trie圖,矩乘)

Description

Input

注意 是0<=P, n , l, m≤ 10.

Output

Sample Input

input 1
3 2 2
1 2
1 2
AB
BA
AA
input 2
3 4 2
1 2
1 2
AABA
ABAA
BAAA

Sample Output

output 1
0.25
0.50
0.25

output 2
0.31
0.33
0.37

解題思路:

可以理解為Trie上倍增佛洛依德做矩乘累和。

程式碼:

  1 #include<cstdio>
  2 #include<cstring>
  3
#include<algorithm> 4 struct trnt{ 5 int ch[26]; 6 int fl; 7 bool fin; 8 }tr[111]; 9 class queue{ 10 public: 11 queue(void){h=1,t=0;return ;} 12 int nxt(int x){if(x+1>=999)return 1;return x+1;} 13 void push(int x){t=nxt(t);line[t]=x;return
;} 14 void pop(void){h=nxt(h);return ;} 15 bool empty(void){return nxt(t)==h;} 16 int front(void){return line[h];} 17 private: 18 int h,t,line[1000]; 19 }Q; 20 int siz; 21 int n,m,l; 22 int ansp[111]; 23 char tmp[111]; 24 double lst[111]; 25 double
ans[111]; 26 double martix[111][111]; 27 double temp[111][111]; 28 double pre[30]; 29 void Insert(char *a,int &plc) 30 { 31 int root=0; 32 int len=l; 33 for(int i=1;i<=len;i++) 34 { 35 int c=a[i]-'A'; 36 if(!tr[root].ch[c]) 37 tr[root].ch[c]=++siz; 38 root=tr[root].ch[c]; 39 } 40 tr[root].fin=true; 41 plc=root; 42 return ; 43 } 44 void Build(void) 45 { 46 int root=0; 47 for(int i=0;i<m;i++) 48 if(tr[root].ch[i]) 49 Q.push(tr[root].ch[i]); 50 while(!Q.empty()) 51 { 52 root=Q.front(); 53 Q.pop(); 54 for(int i=0;i<m;i++) 55 { 56 if(tr[root].ch[i]) 57 { 58 tr[tr[root].ch[i]].fl=tr[tr[root].fl].ch[i]; 59 Q.push(tr[root].ch[i]); 60 }else 61 tr[root].ch[i]=tr[tr[root].fl].ch[i]; 62 } 63 } 64 return ; 65 } 66 int main() 67 { 68 scanf("%d%d%d",&n,&l,&m); 69 for(int i=0;i<m;i++) 70 { 71 int a,b; 72 scanf("%d%d",&a,&b); 73 pre[i]=(double)(a)/(double)(b); 74 } 75 for(int i=1;i<=n;i++) 76 { 77 scanf("%s",tmp+1); 78 Insert(tmp,ansp[i]); 79 } 80 Build(); 81 for(int i=0;i<=siz;i++) 82 { 83 if(tr[i].fin) 84 { 85 martix[i][i]=1.00; 86 continue; 87 } 88 for(int j=0;j<m;j++) 89 martix[i][tr[i].ch[j]]+=pre[j]; 90 91 } 92 int t=70; 93 /*for(int i=0;i<=siz;i++) 94 { 95 for(int j=0;j<=siz;j++) 96 printf("%.2lf ",martix[i][j]); 97 puts(""); 98 }*/ 99 while(t--) 100 { 101 for(int i=0;i<=siz;i++) 102 { 103 for(int j=0;j<=siz;j++) 104 { 105 temp[i][j]=0; 106 for(int k=0;k<=siz;k++) 107 { 108 temp[i][j]+=martix[i][k]*martix[k][j]; 109 } 110 } 111 } 112 for(int i=0;i<=siz;i++) 113 for(int j=0;j<=siz;j++) 114 martix[i][j]=temp[i][j]; 115 } 116 for(int i=1;i<=n;i++) 117 printf("%.2lf\n",martix[0][ansp[i]]); 118 return 0; 119 }