【noip模拟】连环
【题目描述】
惠子说:“连环可解也”。
这说明他是一个破解机关的高手,连连环都能解开,鲁班锁什么的自然不在话下。一位
鲁班的后人非常不服气,于是找到惠子,给他出了一道题。
他首先给了惠子一个长度为 n的字符串s和一个长度为 m 的字符串 t,现在,他有 k 个
询问,每个询问是给出两个整数 L,R,询问任选一对(i,j)满足 1≤i≤L,n≥j≥R,删去 s 的
[i+1,j−1]这个区间的子串,剩下两块拼在一起,求t 在其中的匹配数的期望 e。
惠子非常擅长吹逼,但是对数学却搞不太明白,于是他请你来帮他。
为了防止实数的精度误差,你只需要输出 e×L×(n−R+1)
【输入格式】
第一行一个整数 C,表示数据组数
每组数据,第一行是三个整数n,m,k
接下来一行字符串表示 s
接下来一行字符串表示 t
接下里 k 行,每行两个整数 Li,Ri,表示一组询问
C≤5
n≤5×10^4,m≤100,k≤5×10^4
1≤Li<Ri-1≤n
对于30%的数据,n≤100,k≤100
【输出格式】
对于每组询问,输出一行一个整数表示答案
【样例输入】
1
8 5 4
iamnotsb
iamsb
4 7
3 7
3 8
2 7
【样例输出】
1
1
0
0
【题目分析】
删去一段之后的匹配分两种,一种是本来就匹配的,删除没有影响他,另一种是本来不匹配,删除之后因为两端连接产生的新匹配。
首先考虑第一种:设t的某个匹配为(l,r),推一下公式发现若r≤L,那么这个匹配的贡献为(L−r+1)×(n−R+1)=(L+1)(n−R+1)−r(n−R+1),那么我们可以预处理一下匹配的r的前缀和匹配数的前缀和,就可以O(1)询问出来了。而若l≥R,那么贡献是(l−R+1)×L,也类似的弄两个前缀和出来就好。
现在考虑因为删除中间一坨而产生的新匹配,我们考虑把t拆开成两个非空部分t1,t2,显然这一种的总贡献等同于t1在[1,L]内的匹配数乘以t2在[R,n]内的匹配数,这个也可以预处理一下前缀和,询问的时候枚举拆开的位置就行了。
【code】
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<vector>
using namespace std; const int N = 5e4 + ;
typedef long long ll;
int C, n, m, k, nxt[], revNxt[], lens, lent;
ll pre[N], preCnt[N], last[N], lastCnt[N];
ll tpre[][N], tlast[][N];
char s[N], t[], revt[], revs[N]; inline int read(){
int i = , f = ; char ch = getchar();
for(; (ch < '' || ch > '') && ch != '-'; ch = getchar());
if(ch == '-') f = -, ch = getchar();
for(; ch >= '' && ch <= ''; ch = getchar())
i = (i << ) + (i << ) + (ch - '');
return i * f;
} inline void wr(ll x){
if(x < ) putchar('-'), x = -x;
if(x > ) wr(x / );
putchar(x % + '');
} inline void get_t_nxt(){
for(int i = , j = ; i <= lent; i++){
while(j && t[j + ] != t[i]) j = nxt[j];
if(t[j + ] == t[i]) j++;
nxt[i] = j;
}
} inline void get_r_pre(){
for(int i = , j = ; i <= lens; i++){
pre[i] = pre[i - ];
preCnt[i] = preCnt[i - ];
while(j && s[i] != t[j + ]) j = nxt[j];
if(s[i] == t[j + ]) j++;
if(j == lent){
pre[i] += i;
preCnt[i]++;
j = nxt[j];
}
}
} inline void get_t_rev_nxt(){
for(int i = , j = ; i <= lent; i++){
while(j && revt[j + ] != revt[i]) j = revNxt[j];
if(revt[j + ] == revt[i]) j++;
revNxt[i] = j;
}
} inline void get_l_last(){
for(int i = , j = ; i <= lens; i++){
last[i] = last[i - ];
lastCnt[i] = lastCnt[i - ];
while(j && revs[i] != revt[j + ]) j = revNxt[j];
if(revs[i] == revt[j + ]) j++;
if(j == lent){
last[i] += n - i + ;
lastCnt[i]++;
j = revNxt[j];
}
}
} inline void get_t_pre(){
for(int i = ; i <= lent; i++){
char now[];
int now_nxt[] = {};
for(int j = ; j <= i; j++)
now[j] = t[j];
for(int k = , l = ; k <= i; k++){
while(l && now[l + ] != now[k]) l = now_nxt[l];
if(now[l + ] == now[k]) l++;
now_nxt[k] = l;
}
for(int k = , l = ; k <= lens; k++){
tpre[i][k] = tpre[i][k - ];
while(l && now[l + ] != s[k]) l = now_nxt[l];
if(now[l + ] == s[k]) l++;
if(l == i){
tpre[i][k]++;
l = now_nxt[l];
}
}
}
} inline void get_t_last(){
for(int i = ; i <= lent; i++){
char now[];
int now_nxt[] = {};
for(int j = ; j <= i; j++)
now[j] = revt[j];
for(int k = , l = ; k <= i; k++){
while(l && now[l + ] != now[k]) l = now_nxt[l];
if(now[l + ] == now[k]) l++;
now_nxt[k] = l;
}
for(int k = , l = ; k <= lens; k++){
tlast[i][k] = tlast[i][k - ];
while(l && now[l + ] != revs[k]) l = now_nxt[l];
if(now[l + ] == revs[k]) l++;
if(l == i){
tlast[i][k]++;
l = now_nxt[l];
}
}
}
} int main(){
freopen("lianhuan.in","r",stdin);
freopen("lianhuan.out","w",stdout);
C = read();
while(C--){
n = read(), m = read(), k = read();
scanf("%s", s + );
scanf("%s", t + );
memcpy(revt, t, sizeof t);
memcpy(revs, s, sizeof s);
reverse(revt + , revt + m + );
reverse(revs + , revs + n + );
lent = m;
lens = n;
memset(nxt, , sizeof nxt);
memset(revNxt, , sizeof revNxt);
memset(pre, , sizeof pre);
memset(last, , sizeof last);
memset(tpre, , sizeof tpre);
memset(tlast, , sizeof tlast);
memset(preCnt, , sizeof preCnt);
memset(lastCnt, , sizeof lastCnt);
get_t_nxt();
get_t_rev_nxt();
get_r_pre();
get_l_last();
get_t_pre();
get_t_last();
while(k--){
int L = read(), R = read();
ll ans = ;
ans += preCnt[L] * (L + ) * (n - R + );
ans -= (n - R + ) * pre[L];
ans -= lastCnt[n - R + ] * (R - ) * L;
ans += last[n - R + ] * L;
for(int i = ; i <= lent; i++)
ans += tpre[i][L] * tlast[lent - (i + ) + ][n - R + ];
wr(ans), putchar('\n');
}
}
}
【noip模拟】连环的更多相关文章
- NOIP模拟赛20161022
NOIP模拟赛2016-10-22 题目名 东风谷早苗 西行寺幽幽子 琪露诺 上白泽慧音 源文件 robot.cpp/c/pas spring.cpp/c/pas iceroad.cpp/c/pas ...
- contesthunter暑假NOIP模拟赛第一场题解
contesthunter暑假NOIP模拟赛#1题解: 第一题:杯具大派送 水题.枚举A,B的公约数即可. #include <algorithm> #include <cmath& ...
- NOIP模拟赛 by hzwer
2015年10月04日NOIP模拟赛 by hzwer (这是小奇=> 小奇挖矿2(mining) [题目背景] 小奇飞船的钻头开启了无限耐久+精准采集模式!这次它要将原矿运到泛光之源的矿 ...
- 大家AK杯 灰天飞雁NOIP模拟赛题解/数据/标程
数据 http://files.cnblogs.com/htfy/data.zip 简要题解 桌球碰撞 纯模拟,注意一开始就在袋口和v=0的情况.v和坐标可以是小数.为保险起见最好用extended/ ...
- 队爷的讲学计划 CH Round #59 - OrzCC杯NOIP模拟赛day1
题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的讲学计划 题解:刚开始理解题意理解了好半天,然后发 ...
- 队爷的Au Plan CH Round #59 - OrzCC杯NOIP模拟赛day1
题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的Au%20Plan 题解:看了题之后觉得肯定是DP ...
- 队爷的新书 CH Round #59 - OrzCC杯NOIP模拟赛day1
题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的新书 题解:看到这题就想到了 poetize 的封 ...
- CH Round #58 - OrzCC杯noip模拟赛day2
A:颜色问题 题目:http://ch.ezoj.tk/contest/CH%20Round%20%2358%20-%20OrzCC杯noip模拟赛day2/颜色问题 题解:算一下每个仆人到它的目的地 ...
- CH Round #52 - Thinking Bear #1 (NOIP模拟赛)
A.拆地毯 题目:http://www.contesthunter.org/contest/CH%20Round%20%2352%20-%20Thinking%20Bear%20%231%20(NOI ...
- CH Round #49 - Streaming #4 (NOIP模拟赛Day2)
A.二叉树的的根 题目:http://www.contesthunter.org/contest/CH%20Round%20%2349%20-%20Streaming%20%234%20(NOIP 模 ...
随机推荐
- ajax的get请求与编码
window.onload = function(){ document.getElementById('username').onblur = function(){ var name = docu ...
- (转)Could not execute auto check for display colors using command /usr/bin/xdpyinfo. Check if the DISPL
转自:http://blog.csdn.net/huashnag/article/details/9357517 Starting Oracle Universal Installer... Chec ...
- LoadRunner--录制手机APP脚本
通过LR录制手机脚本的方式有三种: 1)通过安卓模拟器录制: 2)通过抓包录制: 3)通过代理方式录制: 本文使用第二种方式进行录制,首先需要先安装LoadRunner11测试工具,然后安装lr录制A ...
- 具体解释。。设计模式5——DAO。。studying
设计模式5--DAO ★ 场景和问题 在Java程序中,常常须要把数据持久化.也须要获取持久化的数据,可是在进行数据持久化的过程中面临诸多问题 (如:数据源不同.存储类型不同.供应商不同.訪问方式不同 ...
- 特征描述子(feature descriptor) —— HOG(方向梯度直方图)
HOG(Histogram of Oriented Gradients),描述的是图像的局部特征,其命名也暗示了其计算方法,先计算图像中某一区域不同方向上梯度的值,然后累积计算频次,得到直方图,该直方 ...
- 第三方插件将数据转成json
1.需要使用第三方jar commons-beanutils-1.7.0.jar /commons-collections-3.1.jar/commons-lang-2.5jar /commons-l ...
- HDU 1214 圆桌会议 圆环逆序
http://acm.hdu.edu.cn/showproblem.php?pid=1214 题目大意: 一群人围着桌子座,如果在一分钟内一对相邻的人交换位置,问多少分钟后才能得到与原始状态相反的座位 ...
- iOS改动UIButton setTitle字体颜色和调整字体位置
调整Title字体位置 [button setTitleEdgeInsets:UIEdgeInsetsMake(10, 0, 0, 0)]; 四个參数分别代表:上边界,左边界.下边界,右边界 改动UI ...
- C++中使用soap toolkit访问webService详解
使用Visual C++开发SOAP客户端应用 使用Visual C++开发SOAP客户端应用 简介 在本篇文章中,我们将讨论如何使用Visual C++开发一个简单的SOAP客户端应用程序,我们还 ...
- LUA凝视语法
server端代码已经完毕,client正在优化.游戏不久将上线,近期没事做,老大要我開始学习project Anarchy了.里面代码是比較偏爱的C++,包括lua,暂没学过lua.看了下LUA代码 ...