The Problem to Slow Down You
输入:t个测试样例,每个样例输入两个字符串
输出:这两对字符串的回文串可以组成多少对本质不同的回文串
题意:给你两个字符串,然后问你这两字符串中 有多少对本质不同的字符串子序列
#include<iostream>
#include<stdio.h>
#include <algorithm>
#include <string>
#include<string.h>
#include<math.h>
#define ll long long
using namespace std;
const int MAXN = ;
const int N = ;
char s[MAXN],ss[MAXN];//输入的要处理的字符串
ll ans=;
struct Palindromic_Tree
{
int next[MAXN][] ;//next指针,next指针和字典树类似,指向的串为当前串两端加上同一个字符构成
int fail[MAXN] ;//fail指针,失配后跳转到fail指针指向的节点 //回文树里面的一个节点就代表一个回文串 int cnt[MAXN] ;//表示第i个节点代表的回文串出现的次数
int num[MAXN] ; //表示以节点i表示的最长回文串的最右端点为回文串结尾的回文串个数。
int len[MAXN] ;//表示第i个节点代表的回文串长度 int S[MAXN] ;//存放添加的字符
int last ;//指向上一个字符所在的节点,方便下一次add
int n ;//字符数组指针
int p ;//节点指针
int newnode(int l) //在树中新建节点
{
for(int i = ; i < N ; ++ i) next[p][i] = ;
cnt[p] = ;
num[p] = ;
len[p] = l ;
return p ++ ;
}
void init() //初始化
{
p = ;
newnode() ;//建一棵保存长度为偶数的回文树
newnode(-) ;//长度为奇数的回文树
last = ;
n = ;
S[n] = - ;//开头放一个字符集中没有的字符,减少特判
fail[] = ;
}
int get_fail(int x) //和KMP一样,失配后找一个尽量最长的
{
while(S[n - len[x] - ] != S[n])
x = fail[x] ;
return x ;
}
void add(int c,int pos)
{
//printf("%d:",p);//------------>输出节点编号,第一个有回文串的编号时从2开始
c -= 'a';
S[++ n] = c ;
int cur = get_fail(last) ; //通过上一个回文串找这个回文串的匹配位置
//printf("%d ",cur);//输出节点编号p代表的回文串的字符长度
if(!next[cur][c]) //如果这个回文串没有出现过,说明出现了一个新的本质不同的回文串
{
int now = newnode(len[cur] + ) ; //新建节点
fail[now] = next[get_fail(fail[cur])][c] ; //和AC自动机一样建立fail指针,以便失配后跳转
next[cur][c] = now ;
num[now] = num[fail[now]] + ;
//for(int i=pos-len[now]+1; i<=pos; ++i)//--------->输出编号为P代表的回文串
// printf("%c",s[i]);
}
last = next[cur][c] ;
cnt[last] ++ ;
//putchar(10);//------------->输出回车换行
}
void count()
{
for(int i = p - ; i >= ; -- i)
cnt[fail[i]] += cnt[i] ;
//父亲累加儿子的cnt,因为如果fail[v]=u,则u一定是v的子回文串!
}
} pat1,pat2;
void dfs(int x,int y)
{
for(int i=;i<;i++)
{
//son1、son2是节点编号
int son1=pat1.next[x][i];
int son2=pat2.next[y][i];
//cout<<son1<<" "<<son2<<endl;
if(son1&&son2)
{
ans=ans+(ll)pat1.cnt[son1]*pat2.cnt[son2];//ans记录有多少对本质不同的字符串子序列
dfs(son1,son2);
}
}
}
int main()
{
int t,k=;
scanf("%d",&t);
while(t--)
{
ans=;
scanf("%s",s);
int n=strlen(s);
pat1.init();
for(int i=; i<n; i++)
pat1.add(s[i],i);
pat1.count();
scanf("%s",&ss);
int nn=strlen(ss);
pat2.init();
for(int i=;i<nn;i++)
pat2.add(ss[i],i);
pat2.count();
dfs(,);//遍历长度为偶数的回文树
dfs(,);//遍历长度为奇数的回文树
printf("Case #%d: ",k++);
printf("%lld\n",ans);
}
return ;
}
/*
3
abacab
abccab
faultydogeuniversity
hasnopalindromeatall
abbacabbaccab
youmayexpectedstrongsamplesbutnow
*/
The Problem to Slow Down You的更多相关文章
- 2014-2015 ACM-ICPC, Asia Xian Regional Contest G The Problem to Slow Down You 回文树
The Problem to Slow Down You Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://acm.hust.edu.cn/vjud ...
- 回文自动机 + DFS --- The 2014 ACM-ICPC Asia Xi’an Regional Contest Problem G.The Problem to Slow Down You
The Problem to Slow Down You Problem's Link: http://acm.hust.edu.cn/vjudge/problem/viewProblem.actio ...
- CodeForcesGym 100548G The Problem to Slow Down You
The Problem to Slow Down You Time Limit: 20000ms Memory Limit: 524288KB This problem will be judged ...
- UVALive - 7041 The Problem to Slow Down You (回文树)
https://vjudge.net/problem/UVALive-7041 题意 给出两个仅包含小写字符的字符串 A 和 B : 求:对于 A 中的每个回文子串,B 中和该子串相同的子串个数的总和 ...
- UVAlive 7041 The Problem to Slow Down You(回文树)
题目链接: https://icpcarchive.ecs.baylor.edu/index.php?option=com_onlinejudge&Itemid=8&page=show ...
- Codeforces.GYM100548G.The Problem to Slow Down You(回文树)
题目链接 \(Description\) 给定两个串\(S,T\),求两个串有多少对相同回文子串. \(|S|,|T|\leq 2\times 10^5\). \(Solution\) 好菜啊QAQ ...
- 2014-2015 ACM-ICPC, Asia Xian Regional Contest GThe Problem to Slow Down You
http://blog.csdn.net/u013368721/article/details/42100363 回文树 建立两棵回文树,然后count处理一遍就可以了,然后顺着这两棵树的边走下去就 ...
- Gym - 100548G The Problem to Slow Down You
依然是回文树. 我们只需要吧siz[]改成统计两边的siz[][0/1],然后把两个字符中间随便加一个不会出现的字符拼起来,做一遍回文树统计一下就OJBK了 #include<bits/stdc ...
- UVALive - 7041 G - The Problem to Slow Down You
题意:求两个串的公共回文子串个数 题解:建两个回文自动机,从0和1各跑一边就是答案了,因为对于回文自动机来说,从头开始dfs就能找出该字符串的所有回文串 //#pragma GCC optimize( ...
随机推荐
- 转:建立maven私服
一.下载安装与配置 下载 到官网下载:https://www.sonatype.com/download-oss-sonatype image.png 下载的是oss3.x版本的(当时最新版), ...
- DataFrame loc和iloc的区别
loc loc是select by label(name) loc函数是选择dataframe中那一行的index == k的 iloc loc是select by position loc函数是选择 ...
- numpy.eye() 生成对角矩阵
numpy.eye(N,M=None, k=0, dtype=<type 'float'>) 关注第一个第三个参数就行了 第一个参数:输出方阵(行数=列数)的规模,即行数或列数 第三个参数 ...
- WordPress 网站迁移
最近想把本地的WordPress迁移到我的Linux虚拟机里面,是不是很无聊,哈哈哈,接下来就是一过程了,其实这个和迁移到线上是一样的, 1.首先将本地的文件WordPress通过FTP传到虚拟机上: ...
- C语言函数不能返回数组,但可以返回结构体
为什么C语言函数可以返回结构体,却不可以返回数组?有这样的问题并不奇怪,因为C语言数组和结构体本质上都是管理一块内存,那为何编译器要区别对待二者呢? C语言函数为什么不能返回数组? 在C语言程序开发中 ...
- pom.xml文件中properties有什么用
properties标签的作用: 在标签内可以把版本号作为变量进行声明,后面dependency中用到版本号时可以用${变量名}的形式代替,这样做的好处是:当版本号发生改变时,只有更新properti ...
- yp寒假训练一
19年东北四省省赛 做了J G C 补了E H J签到题 G 题意: 给n个正方形的两个斜对角点坐标,问最小的移动可以重叠(移动上下左右一格) 思路: 一开始想的是中心pos移动,但是可能有小数,而且 ...
- 我的B站主页:https://space.bilibili.com/611212 内有视频题解
我的B站主页:https://space.bilibili.com/611212 内有视频题解
- Solidity顺序编程
1.事件 是合约和区块链通讯的一种机制.前端可以监听事件. 使用关键字event(参数);来申请 2.require指令: 使用require指令,使得函数在执行过程中,在不满足某些条件的时候抛出错误 ...
- maven热部署
1.启动tomcat 2.修改 tomat/conf/tomcat-users.xml 配置用户名.密码.角色 manager-gui:图形界面的权限(调试时配置) man ...