题目大意:首先给一个字符集合,这个集合有N个字符,然后需要一个长度为M的句子,但是据子里面不能包含的串有P个,每个串里面的字符都是有字符集和里面的字符构成的,现在想知道最多能构造多少个不重复的句子。
 
分析:跟以前做过的那两题差不多,不过这个不让取余....不过考虑到字符长度也不大,最多也就50,所以使用一般的dp也可以。ps.在做高高精度运算的时候输出答案竟然正着输出了....然后就一直WA....确实有些时间没有敲过高精度题目了。
 
代码如下:
==============================================================================================================================
#include<iostream>
#include<algorithm>
#include<stdio.h>
#include<string.h>
#include<queue>
using namespace std; const int MAXN = ;
const int oo = 1e9+; char WordList[MAXN];
int MaxSon, Matrix[MAXN][MAXN]; struct Ac_Trie
{
int next[MAXN][MAXN], size;
int Fail[MAXN], End[MAXN], root; int newnode()
{
memset(next[size], -, sizeof(next[size]));
Fail[size] = End[size] = false; return size++;
}
void InIt()
{
size = ;
root = newnode();
} void Insert(char s[])
{
int now = root; for(int i=; s[i]; i++)
{
int k = strchr(WordList, s[i]) - WordList; if(next[now][k] == -)
next[now][k] = newnode();
now = next[now][k];
} End[now] = true;
} void GetFail()
{
queue<int> Q;
int now = root; Fail[root] = root; for(int i=; i<MaxSon; i++)
{
if(next[now][i] == -)
next[now][i] = root;
else
{
Fail[next[now][i]] = root;
Q.push(next[now][i]);
}
} while(Q.size())
{
now = Q.front();
Q.pop(); for(int i=; i<MaxSon; i++)
{
if(next[now][i] == -)
next[now][i] = next[Fail[now]][i];
else
{
Fail[next[now][i]] = next[Fail[now]][i];
Q.push(next[now][i]);
}
} End[now] |= End[Fail[now]];
}
}
void GetMatrix()
{
memset(Matrix, false, sizeof(Matrix)); for(int i=; i<size; i++)
for(int k=; k<MaxSon; k++)
{
if(!End[next[i][k]] && !End[i])
Matrix[i][next[i][k]] += ;
}
}
};
Ac_Trie ac; void BigNumAdd(int a[], int num, int b[])
{
for(int i=; i<MAXN; i++)
b[i] += a[i] * num; for(int i=; i<MAXN-; i++)
{
b[i+] += b[i] / ;
b[i] %= ;
}
} int main()
{
int N, P; while(scanf("%d%d%d", &MaxSon, &N, &P) != EOF)
{
char s[MAXN];
ac.InIt(); getchar();
gets(WordList); while(P--)
{
gets(s);
ac.Insert(s);
} ac.GetFail();
ac.GetMatrix(); int dp[][MAXN][MAXN] = {}, op=;
dp[][][] = ;
while(N--)
{
memset(dp[op], false, sizeof(dp[op])); for(int i=; i<ac.size; i++)
for(int j=; j<ac.size; j++)
{
if(Matrix[i][j])
{///dp[op][j] += dp[op^1][i] * Matrix[i][j];
BigNumAdd(dp[op^][i], Matrix[i][j], dp[op][j]);
}
} op ^= ;
} int ans[MAXN] = {}; for(int i=; i<ac.size; i++)
BigNumAdd(dp[op^][i], , ans); N = MAXN - ;
while(ans[N] == && N > )
N--; for(int i=N; i>=; i--)
printf("%d", ans[i]);
printf("\n");
} return ;
}

Censored! - POJ 1625(ac自动机+简单dp+高精度运算)的更多相关文章

  1. Censored! POJ - 1625 AC自动机+大数DP

    题意: 给出一n种字符的字典,有p个禁用的单词, 问能组成多少个不同的长度为m的合法字符串.(m<=50) 题解: 是不是个我们之前做的题目非常非常像,题意都一样. 直接将上次写的AC自动机+矩 ...

  2. Ring HDU - 2296 AC自动机+简单DP和恶心的方案输出

    题意: 就是现在给出m个串,每个串都有一个权值,现在你要找到一个长度不超过n的字符串, 其中之前的m个串每出现一次就算一次那个字符串的权值, 求能找到的最大权值的字符串,如果存在多个解,输出最短的字典 ...

  3. 小明系列故事――女友的考验 HDU - 4511 AC自动机+简单DP

    题意:自己看题目,中文体面. 题解: 把所有不能走的路径放入AC自动机中. 然后DP[i][j]表示走到 i 这个点,且位于AC自动机 j 这个节点最短距离 然后直接DP即可.注意一点会爆int #i ...

  4. 【HDU3530】 [Sdoi2014]数数 (AC自动机+数位DP)

    3530: [Sdoi2014]数数 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 682  Solved: 364 Description 我们称一 ...

  5. 关于AC自动机和DP的联系

    首先是描述个大概.不说一些特殊的DP 或者借用矩阵来状态转移 (这些本质都是一样的). 只讲AC自动机和DP的关系(个人理解). AC自动机 又可以叫做状态机. 我一开始的认为.AC 自动机提供了一些 ...

  6. 【bzoj3530】[Sdoi2014]数数 AC自动机+数位dp

    题目描述 我们称一个正整数N是幸运数,当且仅当它的十进制表示中不包含数字串集合S中任意一个元素作为其子串.例如当S=(22,333,0233)时,233是幸运数,2333.20233.3223不是幸运 ...

  7. BZOJ 3530 [SDOI2014]数数 (Trie图/AC自动机+数位DP)

    题目大意:略 裸的AC自动机+数位DP吧... 定义f[i][x][0/1]表示已经匹配到了第i位,当前位置是x,0表示没到上限,1到上限,此时数是数量 然而会出现虚拟前导零,即前几位没有数字的情况, ...

  8. POJ 3691 (AC自动机+状态压缩DP)

    题目链接:  http://poj.org/problem?id=3691 题目大意:给定N个致病DNA片段以及一个最终DNA片段.问最终DNA片段最少修改多少个字符,使得不包含任一致病DNA. 解题 ...

  9. Walk Through Squares HDU - 4758 AC自动机+简单状压DP

    题意:给你两个串,求用m个R,n个D能组成多少个包含这两个串 题解:先构造一个AC自动机记录每个状态包含两个串的状态, 状态很容易定义 dp[i][j][k][status]表示在AC自动机K这个节点 ...

随机推荐

  1. 【原创】不用封装jar包 直接引入工程使用的方法(类似android的 is Library功能)

    1.制作lib工程,这里我简单制作一个测试类 2.eclipse中 java Project工程引入方法 2.1.新建个java工程,在属性配置中选择 "Java Build Path&qu ...

  2. oracle 报Ora-01008错误:oracle 并非所有变量都已绑定的原因.TO_number();动态执行select..into..语句时

    1.sql_temp := 'UPDATE B38_back SET '||code||'=TO_NUMBER(nvl('||:NEW.BACAI||',0))+'||OnMonth || ' WHE ...

  3. php中文乱码

    一.         首先是PHP网页的编码 1.     php文件本身的编码与网页的编码应匹配 a.     如果欲使用gb2312编码,那么php要输出头:header(“Content-Typ ...

  4. Bootstrap_Javascript_弹窗

    一. 结构分析 Bootstrap框架中的模态弹出框,分别运用了“modal”.“modal-dialog”和“modal-content”样式,而弹出窗真正的内容都放置在“modal-content ...

  5. php 上传视频的代码

    <html> <head> <meta http-equiv="Content-Type" content="text/html; char ...

  6. IS打包

    1. 目的 让用户可以通过运行一个安装程序,安装程序到系统中正常运行. 2. 注意 当我们用项目向导生成的新项目时,InstallShield只为我们生成两个事件,分别是OnFirstUIBefore ...

  7. xml和html之间相互转换

    一.xml转换html xml+xslt是典型的数据与表现分离的设计方式.当然,你可以直接转换成HTML,但是如果你要进行整体变化的时候,XML+XSLT的优势就体现出来了.同样的数据,因为你已经有X ...

  8. Spark的RDD编程(二)公众号undefined110

    创建RDD有两种方式:①读取外部数据集,lines=sc.textFile("README.md").②对一个集合进行并行化,lines=sc.parallelize([" ...

  9. 【转】近百个Android优秀开源项目

    近百个Android优秀开源项目   Android开发又将带来新一轮热潮,很多开发者都投入到这个浪潮中去了,创造了许许多多相当优秀的应用.其中也有许许多多的开发者提供了应用开源项目,贡献出他们的智慧 ...

  10. [BZOJ 1042] [HAOI2008] 硬币购物 【DP + 容斥】

    题目链接:BZOJ - 1042 题目分析 首先 Orz Hzwer ,代码题解都是看的他的 blog. 这道题首先使用DP预处理,先求出,在不考虑每种硬币个数的限制的情况下,每个钱数有多少种拼凑方案 ...