UVAlive 3490 AC自动机+(整数)高斯消元
来源:互联网 发布:php微信商城三级分销 编辑:程序博客网 时间:2024/06/05 14:07
题意:
题目链接:https://vjudge.net/problem/UVALive-3490
给出一个字符串S和前n个英文大写字母,组成一个字符串,当构造出子串S时停止,则该字符串期望长度是多少。
思路:
AC自动机+高斯消元,与HDU 5955一个套路:http://blog.csdn.net/bahuia/article/details/53034010
这题坑的时直接用double的高斯消元误差太大,连样例都出不来,必须改成整形的高斯消元,学习别人的写法,存个板子。
代码:
#include <bits/stdc++.h>using namespace std;typedef long long LL;const int MAXN = 100;struct ACauto { int next[MAXN][26], fail[MAXN], end[MAXN]; int root, sz; int newnode() { for (int i = 0; i < 26; i++) next[sz][i] = -1; end[sz++] = 0; return sz - 1; } void init() { sz = 0; root = newnode(); } int idx(char c) { return c - 'A'; } void insert(char *buf) { int len = strlen(buf); int now = root; for (int i = 0; i < len; i++) { int id = idx(buf[i]); if (next[now][id] == -1) next[now][id] = newnode(); now = next[now][id]; } end[now]++; } void build() { queue <int> Q; fail[root] = root; for (int i = 0; i < 26; i++) { if (next[root][i] == -1) next[root][i] = root; else { fail[next[root][i]] = root; Q.push(next[root][i]); } } while (!Q.empty()) { int now = Q.front(); Q.pop(); for (int i = 0; i < 26; i++) { if (next[now][i] == -1) next[now][i] = next[fail[now]][i]; else { fail[next[now][i]] = next[fail[now]][i]; Q.push(next[now][i]); } } } }} ac;int equ, var;LL a[MAXN][MAXN], x[MAXN];void Gauss()//表示用double版本的高斯消元求解,最后还原成整数的方法因为误差跪掉了....{ for(int i = 0; i < equ; i++) { int r = i; while(r < equ && !a[r][i]) r++; if(r != i)//找到第r列不是0的之后交换至r行 { for(int j = 0; j < var; j++) swap(a[r][j], a[i][j]); swap(x[r], x[i]); } for(int k = i + 1; k < equ; k++) if(a[k][i])//将下面所有行的第i列变成0 { LL tmp = a[k][i];//两组互相乘上对面的第i列的数作差即可 for(int j = i; j < var; j++) a[k][j] = a[k][j] * a[i][i] - tmp*a[i][j]; x[k] = x[k]*a[i][i] - tmp*x[i]; } } //对剩下的三角矩阵递推求解 for(int i = equ - 1; i >= 0; i--) { for(int j = i + 1; j < var; j++) x[i] -= x[j]*a[i][j]; x[i] /= a[i][i]; }}char str[MAXN];int main() { //freopen("in.txt", "r", stdin); int T, cs = 0; scanf("%d", &T); while (T--) { int n; scanf("%d%s", &n, str); ac.init(); ac.insert(str); ac.build(); equ = var = ac.sz; memset(a, 0, sizeof(a)); memset(x, 0, sizeof(x)); //cout << ac.sz << endl; for (int u = 0; u < ac.sz - 1; u++) { a[u][u] = n; for (int id = 0; id < n; id++) { int v = ac.next[u][id]; a[u][v] -= 1; } a[u][var] = n; x[u] = n; } a[equ - 1][var - 1] = 1; a[equ - 1][var] = 0; x[equ - 1] = 0; Gauss(); printf("Case %d:\n%lld\n", ++cs, x[0]); if (T) puts(""); } return 0;}
阅读全文
0 0
- UVAlive 3490 AC自动机+(整数)高斯消元
- UVaLive 3490 - Generator (AC自动机 期望DP 高斯消元)
- UVALive 3490 Generator(AC自动机+dp+高斯消元)
- uvalive 3490 解法二 AC自动机 + 高斯消元
- UVALive 3490 (LA 3940) || ZOJ 2619 Generator AC自动机(或KMP) + 整数高斯消元 + 数学期望
- UVALive 4670(AC自动机)
- UVALive 6495 Probability Paradox AC自动机+高斯消元
- UVALive 4670 - Dominating Patterns (AC自动机)
- UVALIVE Dominating Patterns (AC自动机)
- UVALive 4670 (AC自动机)
- UVALive 4670 AC自动机
- UVALive-4126 AC自动机
- UVALive 4670 Dominating Patterns(AC自动机模板题)
- UVALive 4126 Password Suspects(AC自动机 + DP)
- UVaLive 4126 - Password Suspects (AC自动机 DP)
- UVaLive/LA 6806 Hari Merdeka(AC自动机,DP)
- UVALive 4126 Password Suspects(AC自动机+dp)
- UVALive 4126 Password Suspects(AC自动机 套 DP)
- e3mall Day07
- 深入理解 js this 绑定 (尾部有总结和面试题解析 )
- App适配iOS 11
- HttpURLConnection之多线程下载
- java ThreadLocal(应用场景及使用方式及原理)
- UVAlive 3490 AC自动机+(整数)高斯消元
- 应聘嵌入式工程师笔试常考之宏定义的优缺点
- ios 两句话解决,从无导航栏push到有导航栏界面,顶部闪现空白问题
- ios实现UITableView左滑删除-复制即用
- Nodejs操作Mongodb增删查改
- MySQL 存储引擎InnoDB和MyISAM的区别
- OpenStack社区组件-存储、备份和恢复
- 《荒岛求生》
- poj-1659-Frogs' Neighborhood-图论-Havel-Hakimi定理-java