Separate String
Separate String
时间限制: 1 Sec 内存限制: 128 MB
提交: 50 解决: 16
题目描述
For example, the following 4 separation methods satisfy the condition when t=abab and S={a,ab,b}.
a,b,a,b
a,b,ab
ab,a,b
ab,ab
Your task is to count the number of ways to separate t. Because the result can be large, you should output the remainder divided by 1,000,000,007.
输入
N
s1
:
sN
t
The first line consists of an integer N (1≤N≤100,000) which is the number of the elements of S. The following N lines consist of N distinct strings separated by line breaks. The i-th string si represents the i-th element of S. si consists of lowercase letters and the length is between 1 and 100,000, inclusive. The summation of length of si (1≤i≤N) is at most 200,000. The next line consists of a string t which consists of lowercase letters and represents the string to be separated and the length is between 1 and 100,000, inclusive.
输出
样例输入
3
a
b
ab
abab
样例输出
4 题解:在kuangbin的板子当中增加ln(以此为结尾的字符串的长度),true_nex(也可以叫做true_fail,用于表示真正有效的fail值,即存在以此为结尾的字符串)数组;
true_nex数组层层计算即可,因为上层的true_nex肯定已被正确计算。然后在query函数里面跑一个简单的DP即可。 AC代码:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll mod=1e9+;
const int maxn=1e6+;
ll dp[maxn];
struct Trie
{
int nxt[][],fail[],endd[],ln[],true_nex[];
int root,L;
int newnode(){
for(int i=;i<;i++){
nxt[L][i]=-;
}
true_nex[L]=;
ln[L]=;
endd[L++]=;
return L-;
}
void init(){
L=;
root=newnode();
}
void insert(char buf[])
{
int len=strlen(buf);
int now=root;
for(int i=;i<len;i++){
if(nxt[now][buf[i]-'a']==-){
nxt[now][buf[i]-'a']=newnode();
ln[nxt[now][buf[i]-'a']]=ln[now]+;
}
now=nxt[now][buf[i]-'a'];
}
endd[now]++;
}
void build()
{
queue<int> Q;
fail[root]=root;true_nex[root]=root;
for(int i=;i<;i++){
if(nxt[root][i]==-){
nxt[root][i]=root;
}
else{
fail[nxt[root][i]]=root;
true_nex[nxt[root][i]]=root;/**/
Q.push(nxt[root][i]);
}
}
while(!Q.empty())
{
int now=Q.front();
Q.pop();
for(int i=;i<;i++)
{
if(nxt[now][i]==-){
nxt[now][i]=nxt[fail[now]][i];
}
else{
fail[nxt[now][i]]=nxt[fail[now]][i];
if(endd[nxt[fail[now]][i]]>) true_nex[nxt[now][i]]=nxt[fail[now]][i];/**/
else true_nex[nxt[now][i]]=true_nex[nxt[fail[now]][i]];/**/
Q.push(nxt[now][i]);
}
}
}
}
ll query(char buf[])
{
int len=strlen(buf);
int now=root;
int res=;
dp[]=;
for(int i=;i<len;i++)
{
now=nxt[now][buf[i]-'a'];
int temp=now;
while(temp!=root)
{
dp[i+]=(dp[i+]+dp[i+-ln[temp]]*endd[temp])%mod;
temp=true_nex[temp];
}
}
return dp[len];
}
}ac;
int n;
char buf[maxn];
int main()
{
int t=;
for(;t;t--)
{
scanf("%d",&n);
ac.init();
while(n--)
{
scanf("%s",buf);
ac.insert(buf);
}
ac.build();
scanf("%s",buf);
printf("%lld\n",ac.query(buf));
}
return ;
}
Separate String的更多相关文章
- 10 Things Every Java Programmer Should Know about String
String in Java is very special class and most frequently used class as well. There are lot many thin ...
- 4 .Swift函数|闭包
在编程中,我们常把能完成某一特定功能的一组代码,并且带有名字标记类型叫做函数,在C语言中,我们知道函数名就是一个指针,它指向了函数体内代码区的第一行代码的地址,在swift中也具有同样的功效. 在Sw ...
- URL Parsing
[URL Parsing] urllib.parse.urlparse(urlstring, scheme='', allow_fragments=True) Parse a URL into six ...
- Swift函数|闭包
在编程中,我们常把能完成某一特定功能的一组代码,并且带有名字标记类型叫做函数,在C语言中,我们知道函数名就是一个指针,它指向了函数体内代码区的第一行代码的地址,在swift中也具有同样的功效. 在Sw ...
- .NET 并行编程——任务并行
本文内容 并行编程 任务并行 隐式创建和运行任务 显式创建和运行任务 任务 ID 任务创建选项 创建任务延续 创建分离的子任务 创建子任务 等待任务完成 组合任务 任务中的异常处理 取消任务 Task ...
- bsdasm
bsdasm 来源 http://www.int80h.org/bsdasm/ Preface by G. Adam StanislavWhiz Kid Technomagic Assembly la ...
- php数组与字符串转换
1.将字符串转换成数组的几个函数: (1)explode(separate,string) 示例:$str = "Hello world It's a beautiful day" ...
- Base Conversion In PHP and javascript
http://www.exploringbinary.com/base-conversion-in-php-using-built-in-functions/ http://www.binarycon ...
- C string.h 常用函数
参考:http://womendu.iteye.com/blog/1218155 http://blog.csdn.net/zccst/article/details/4294565 还有一些,忘记了 ...
随机推荐
- ApkUtils
import android.content.Context; import android.content.Intent; import android.content.pm.PackageInfo ...
- Swift开源parser
https://www.prowidesoftware.com/products/core https://github.com/prowide/prowide-core-examples/blob/ ...
- python之scrapy携带Cookies模拟登陆
知识点 """ scrapy两种模拟登陆: 1.直接携带cookie 2.找到发送post请求的url地址,带上信息,发送请求 应用场景: 1.cookie过期时间很长, ...
- Scala面向对象01
- Linux新增开放端口
CentOS系统 开放端口的方法: 方法一:命令行方式 1. 开放端口命令: /sbin/iptables -I INPUT -p tcp --dport 8080 -j ...
- SpringMVC中实现Bean Validation(JSR 303 JSR 349 JSR 380)
JSR 303是针对bean数据校验提出的一个规范.使用注解方式实现数据校验. 每个注解的用法这里就不多介绍,请移步JSR 303 - Bean Validation 介绍及最佳实践 笔者上面提到的J ...
- Xib设置label自动换行和Label的顶部对齐
真的是不想说自己了,一个Xib纠结了一天,简直了,整整被虐了一上午啊...... 不知道这是Xcode8的问题呢....还是我的Xib约束什么的问题..... 只想说的是,以前也是这么设置的,明明可以 ...
- Swift 3.0 闭包的定义和使用
// // ViewController.swift // 闭包的定义和使用 // // Created by 思 彭 on 16/9/17. // Copyright © 2016年 思 彭. Al ...
- 【JVM学习笔记】线程上下文类加载器
有许多地方能够看到线程上下文类加载的设置,比如在sun.misc.Launcher类的构造方法中,能够看到如下代码 先写一个例子建立感性认识 public class Test { public st ...
- Flask之上下文管理机制
前引 在了解flask上下文管理机制之前,先来一波必知必会的知识点. 面向对象双下方法 首先,先来聊一聊面向对象中的一些特殊的双下划线方法,比如__call__.__getattr__系列.__get ...