poj 2778 DNA Sequence

http://poj.org/problem?id=2778

  跟上一篇一样,都是自动机加矩阵的题。不过这次因为忘记将答案取模了,所以wa了一次。。。- -这次的代码相对整齐了点,没有上一篇那么乱了。。。

代码如下:

View Code
  1 #include <cstdio>
  2 #include <iostream>
  3 #include <cstring>
  4 #include <map>
  5 #include <algorithm>
  6 #include <cassert>
  7 
  8 using namespace std;
  9 
 10 const int matSize = 105;
 11 const int initMod = 100000;
 12 int curSize = matSize;
 13 typedef long long ll;
 14 
 15 struct Matrix {
 16     ll val[matSize][matSize];
 17 
 18     Matrix (bool ONE = false) {
 19         for (int i = 0; i < curSize; i++) {
 20             for (int j = 0; j < curSize; j++) {
 21                 val[i][j] = 0;
 22             }
 23             val[i][i] = ONE;
 24         }
 25     }
 26 
 27     void print(int _l = curSize, int _w = curSize) {
 28         for (int i = 0; i < _l; i++) {
 29             for (int j = 0; j < _w; j++) {
 30                 if (j) putchar(' ');
 31                 cout << val[i][j];
 32             }
 33             puts("");
 34         }
 35     }
 36 } Base, op;
 37 
 38 Matrix operator * (Matrix &_a, Matrix &_b) {
 39     Matrix ret = Matrix();
 40 
 41     for (int i = 0; i < curSize; i++) {
 42         for (int k = 0; k < curSize; k++) {
 43             if (_a.val[i][k]) {
 44                 for (int j = 0; j < curSize; j++) {
 45                     ret.val[i][j] += _a.val[i][k] * _b.val[k][j];
 46                     ret.val[i][j] %= initMod;
 47                 }
 48             }
 49         }
 50     }
 51 
 52     return ret;
 53 }
 54 
 55 Matrix operator ^ (Matrix &__a, ll _p) {
 56     Matrix _a = __a;
 57     Matrix ret = Matrix(true);
 58 
 59     while (_p) {
 60         if (_p & 1) {
 61             ret = ret * _a;
 62         }
 63         _a = _a * _a;
 64         _p >>= 1;
 65     }
 66 
 67     return ret;
 68 }
 69 
 70 const int maxNode = 105;
 71 const int kind = 4;
 72 int root, cntNode;
 73 int Q[maxNode], qh, qt;
 74 
 75 struct Node {
 76     int child[kind];
 77     int fail;
 78     bool end;
 79 
 80     Node() {
 81         for (int i = 0; i < kind; i++) {
 82             child[i] = -1;
 83         }
 84         fail = -1;
 85         end = false;
 86     }
 87 } node[maxNode];
 88 
 89 map<char, int> con;
 90 
 91 void init() {
 92     con.clear();
 93     con['A'] = 0;
 94     con['T'] = 1;
 95     con['C'] = 2;
 96     con['G'] = 3;
 97 }
 98 
 99 void initTrie() {
100     root = 0;
101     cntNode = 1;
102     node[root] = Node();
103 }
104 
105 void insert(char *_s) {
106     int cur = root;
107 
108     while (*_s) {
109         int index = con[*_s];
110 
111         if (node[cur].child[index] == -1) {
112             node[cur].child[index] = cntNode;
113             node[cntNode] = Node();
114             cntNode++;
115         }
116         cur = node[cur].child[index];
117         _s++;
118     }
119     node[cur].end = true;
120 }
121 
122 void buildMat() {
123     Base = Matrix();
124     op = Matrix();
125     Base.val[0][0] = 1;
126 
127     qh = qt = 0;
128     Q[qt++] = root;
129     node[root].fail = root;
130 
131     while (qh < qt) {
132         int cur = Q[qh++];
133 
134         for (int i = 0; i < kind; i++) {
135             int c = node[cur].child[i];
136 
137             if (~c) {
138                 if (cur == root) {
139                     node[c].fail = root;
140                 } else {
141                     node[c].fail = node[node[cur].fail].child[i];
142                     if (node[node[c].fail].end) node[c].end = true;
143                 }
144                 Q[qt++] = c;
145             } else {
146                 if (cur == root) {
147                     node[cur].child[i] = root;
148                 } else {
149                     node[cur].child[i] = node[node[cur].fail].child[i];
150                 }
151             }
152         }
153     }
154 
155     for (int i = 0; i < cntNode; i++) {
156         if (node[i].end) continue;
157 
158         for (int j = 0; j < kind; j++) {
159             if (node[node[i].child[j]].end) continue;
160             op.val[i][node[i].child[j]]++;
161         }
162     }
163 
164 //    op.print();
165 }
166 
167 int main() {
168     int n, m;
169 
170 //    freopen("in", "r", stdin);
171     init();
172     while (cin >> n >> m) {
173         char buf[15];
174 
175         initTrie();
176         while (n--) {
177             cin >> buf;
178             insert(buf);
179 //            puts("Inserted");
180         }
181         curSize = cntNode;
182         buildMat();
183         op = op ^ m;
184         Base = Base * op;
185 
186         ll ans = 0;
187 
188         for (int i = 0; i < curSize; i++) {
189             ans += op.val[0][i];
190         }
191         cout << ans % initMod<< endl;
192     }
193 
194     return 0;
195 }

 

——written by Lyon

转载于:https://www.cnblogs.com/LyonLys/archive/2012/10/05/poj_2778_Lyon.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值