题意

题目链接

Sol

直接在SAM上乱搞

枚举前缀,用SAM统计可以匹配的后缀,具体在匹配的时候维护和当前节点能匹配的最大值

然后再把parent树上的点的贡献也统计上,这部分可以爆跳parent树(假的,因为这题数据随机),也可以直接树形dp一波记下每个点被统计的次数

#include<bits/stdc++.h>
#define LL long long
using namespace std;
const int MAXN = 4e5 + 10;
int N1, N2;
char a[MAXN], b[MAXN];
// struct SAM {
int fa[MAXN], ch[MAXN][26], len[MAXN], siz[MAXN], tot, las, root, f[MAXN], g[MAXN];
vector<int> v[MAXN];
// SAM() {
// root = las = tot = 1;
// }
void insert(int x) {
int now = ++tot, pre = las; las = now; siz[now] = 1;
len[now] = len[pre] + 1;
for(; pre && !ch[pre][x]; pre = fa[pre]) ch[pre][x] = now;
if(!pre) fa[now] = root;
else {
int q = ch[pre][x];
if(len[pre] + 1 == len[q]) fa[now] = q;
else {
int ns = ++tot; fa[ns] = fa[q]; len[ns] = len[pre] + 1;
memcpy(ch[ns], ch[q], sizeof(ch[q]));
fa[q] = fa[now] = ns;
for(; pre && ch[pre][x] == q; pre = fa[pre]) ch[pre][x] = ns;
}
}
}
void Build() {
for(int i = 2; i <= tot; i++) v[fa[i]].push_back(i);
}
void dfs(int x, int opt) {
for(int i = 0; i < v[x].size(); i++) {
int to = v[x][i];
dfs(to, opt);
if(opt == 1) siz[x] += siz[to];
if(opt == 2) f[x] += f[to] + g[to];
}
}
// }sam;
int main() {
root = las = tot = 1;
scanf("%s%s", a + 1, b + 1);
N1 = strlen(a + 1); N2 = strlen(b + 1);
for(int i = 1; i <= N1; i++) insert(a[i] - 'a');
Build(); dfs(root, 1);
int now = root, cur = 0; LL ans = 0;
for(int i = 1; i <= N2; i++) {
int x = b[i] - 'a';
if(ch[now][x]) now = ch[now][x], cur++;
else {
while(!ch[now][x] && now) now = fa[now];
if(!now) now = 1, cur = 0;
else cur = len[now] + 1, now = ch[now][x];
}
ans += 1ll * (cur - len[fa[now]]) * siz[now];
g[now]++;
//int tmp = fa[now];
//while(tmp != 1) ans += (len[tmp] - len[fa[tmp]]) * siz[tmp], tmp = fa[tmp];
}
dfs(root, 2);
for(int i = 1; i <= tot; i++) ans += 1ll * (len[i] - len[fa[i]]) * siz[i] * f[i];
cout << ans;
return 0;
}
/*
aa
aa acb
abc ababababba
abbababab
*/

BZOJ4566: [Haoi2016]找相同字符(后缀自动机)的更多相关文章

  1. [BZOJ4566][Haoi2016]找相同字符 后缀自动机+dp

    4566: [Haoi2016]找相同字符 Time Limit: 20 Sec  Memory Limit: 256 MBSubmit: 1212  Solved: 694[Submit][Stat ...

  2. BZOJ 4566: [Haoi2016]找相同字符 [后缀自动机]

    4566: [Haoi2016]找相同字符 Time Limit: 20 Sec  Memory Limit: 256 MBSubmit: 275  Solved: 155[Submit][Statu ...

  3. HAOI2016 找相同字符 后缀自动机

    两个串,考虑一建一跑.枚举模式串的位置\(i\),考虑每次统计以\(i\)结尾的所有符合要求的串.在后缀自动机上走时记录当前匹配长度\(curlen\),则当前节点的贡献是\((curlen-len[ ...

  4. BZOJ4566 [Haoi2016]找相同字符【SAM】

    BZOJ4566 [Haoi2016]找相同字符 给定两个字符串\(s和t\),要求找出两个字符串中所有可以相互匹配的子串对的数量 首先考虑可以怎么做,我们可以枚举\(t\)串的前缀\(t'\),然后 ...

  5. [Bzoj4566][Haoi2016]找相同字符(广义后缀自动机)

    4566: [Haoi2016]找相同字符 Time Limit: 20 Sec  Memory Limit: 256 MBSubmit: 861  Solved: 495[Submit][Statu ...

  6. 【BZOJ4566】[Haoi2016]找相同字符 后缀数组+单调栈

    [BZOJ4566][Haoi2016]找相同字符 Description 给定两个字符串,求出在两个字符串中各取出一个子串使得这两个子串相同的方案数.两个方案不同当且仅当这两 个子串中有一个位置不同 ...

  7. [HAOI2016] 找相同字符 - 后缀数组,单调栈

    [HAOI2016] 找相同字符 Description 给定两个字符串,求出在两个字符串中各取出一个子串使得这两个子串相同的方案数.两个方案不同当且仅当这两个子串中有一个位置不同. \(n,m \l ...

  8. BZOJ4566 Haoi2016 找相同字符【广义后缀自动机】

    Description 给定两个字符串,求出在两个字符串中各取出一个子串使得这两个子串相同的方案数.两个方案不同当且仅当这两 个子串中有一个位置不同. Input 两行,两个字符串s1,s2,长度分别 ...

  9. BZOJ4566: [Haoi2016]找相同字符

    Description 给定两个字符串,求出在两个字符串中各取出一个子串使得这两个子串相同的方案数.两个方案不同当且仅当这两 个子串中有一个位置不同. Input 两行,两个字符串s1,s2,长度分别 ...

随机推荐

  1. 在node中使用promise上传图片到七牛云

    为了分摊个人服务器压力.提升图片下载上传的速度,使用七牛云保存用户上传的图片. 后台基于express搭建的,上传使用七牛云第三方nodejs-sdk.由于七牛云上传图片只能单个进行,并且考虑到上传完 ...

  2. 电脑网络IP固定地址自动改变!

    今天电脑的固定IP地址每次重启设备,会自动改变一次.所以每次重启电脑都要手动重设IP地址.网关.DNS及高级选项中的ip设置. 高级选项中的ip设置每次都有2个ip,都要我删除一个.我都崩溃了,还以为 ...

  3. OpenCV --- 实现两幅图像并排合并(ROI)

    Mat img1 = imread("1.png"); Mat img2 = imread("2.png"); int height = img1.rows; ...

  4. Linux必备命令

      目录                                                              概述 常用系统工作命令 系统状态检测命令 工作目录切换命令 文本文件 ...

  5. POJ 1032

    #include<iostream> using namespace std; int main() { int n; int num; ; int i,j; cin>>num ...

  6. J02-Java IO流总结二 《概述》

    1  流的概念 流是一个信息的通道,通过通道可以访问通道连接的文件对象. 2  流的分类 根据流中数据的流向,可分为输入流和输出流 输入流:从其他的地方流入到程序内存中的,比如InputStream. ...

  7. C语言 for循环之阶乘的算法

    int n; scanf("%d", &n); int fact = 1; int i = 1; while ( i <= n ) { fact *=i; i++; ...

  8. 关于防止表单form重复提交的方式

    表单重复提交: 1.第一种:添加以后刷新页面(刷新的是Servlet) 2.第二种:重复点击提交按钮. * 使用令牌机制:(防止表单重复提交) * 在表单页面中 生成一个令牌 * 将这个令牌保存在se ...

  9. 如何在window server IIS上部署可以使用web deploy?

    环境: windows server2012 方式1: 1,下载"wpilauncher.exe" Web平台安装程序.下载地址:http://www.microsoft.com/ ...

  10. VUE之文字跑马灯效果

    VUE之文字跑马灯效果 1.效果演示 2.相关代码 <!DOCTYPE html> <html lang="en"> <head> <me ...