$n \leq 100000$的一文本串,给$m \leq 100000$个询问,每次问一小串在文本串的哪一个最短的子串里出现指定次数。注意,询问串互不相同,且总长度$\leq 100000$。

比赛时不会分析复杂度QAQ没想到这么简单

互不相同的询问串,不同的长度会只有根号个。而每个长度的出现次数都是n级别的,因此总的出现次数是$n\sqrt{n}$,只要想出$O(串长+出现次数)$的匹配算法就行了。

然后SA,SAM,AC,bitset挑个写就行了。写了AC。

 //#include<iostream>
#include<cstring>
#include<cstdio>
//#include<time.h>
//#include<complex>
#include<set>
//#include<queue>
#include<algorithm>
#include<stdlib.h>
using namespace std; #define LL long long
int qread()
{
char c; int s=; while ((c=getchar())<'' || c>'');
do s=s*+c-''; while ((c=getchar())>='' && c<=''); return s;
} //Pay attention to '-' , LL and double of qread!!!! int n,lq;
#define maxn 200011
struct Edge{int to,next;}edge[maxn<<]; int first[maxn],le=;
void in(int x,int y) {Edge &e=edge[le]; e.to=y; e.next=first[x]; first[x]=le++;} set<int> ss[maxn]; int ls=,bel[maxn];
struct AC
{
struct Node{int ch[],fail;}a[maxn];
int num[maxn],size;
AC() {size=; memset(a[].ch,,sizeof(a[].ch));}
int insert(char *s,int id)
{
int now=,m=strlen(s);
for (int i=;i<m;i++)
{
int p=s[i]-'a';
if (!a[now].ch[p])
{
int x=++size;
a[now].ch[p]=x;
}
now=a[now].ch[p];
}
num[id]=now;
return now;
} int que[maxn],head,tail;
void makefail()
{
head=tail=;
for (int i=;i<;i++)
{
int u=a[].ch[i];
if (u) que[tail++]=u,a[u].fail=;
}
while (head!=tail)
{
int x=que[head++];
for (int i=;i<;i++)
{
int u=a[x].ch[i];
if (!u) {a[x].ch[i]=a[a[x].fail].ch[i]; continue;}
que[tail++]=u;
a[u].fail=a[a[x].fail].ch[i];
}
}
}
void buildtree() {for (int i=;i<=size;i++) in(a[i].fail,i);} void pei(char *s)
{
int n=strlen(s),now=;
for (int i=;i<n;i++)
{
now=a[now].ch[s[i]-'a'];
if (!bel[now]) bel[now]=++ls;
ss[bel[now]].insert(i);
}
}
}ac; int ques[maxn],kk[maxn],ll[maxn],ans[maxn]; void bing(int x)
{
int Max=x;
for (int i=first[x];i;i=edge[i].next)
{
Edge &e=edge[i];
bing(e.to);
if (ss[bel[e.to]].size()>ss[bel[Max]].size()) Max=e.to;
} for (int i=first[x];i;i=edge[i].next)
{
Edge &e=edge[i]; if (e.to==Max) continue;
for (auto j=ss[bel[e.to]].begin();j!=ss[bel[e.to]].end();j++) ss[bel[Max]].insert(*j);
}
if (Max!=x)
{
for (auto j=ss[bel[x]].begin();j!=ss[bel[x]].end();j++) ss[bel[Max]].insert(*j);
bel[x]=bel[Max];
} if (ques[x])
{
vector<int> p;
for (auto j=ss[bel[x]].begin();j!=ss[bel[x]].end();j++) p.push_back(*j);
int Ans=0x3f3f3f3f;
for (unsigned int k=kk[ques[x]],j=k-;j<p.size();j++) Ans=min(Ans,p[j]-p[j-k+]);
if (Ans==0x3f3f3f3f) ans[ques[x]]=-;
else ans[ques[x]]=Ans+ll[ques[x]];
}
} char s[maxn],t[maxn];
int main()
{
scanf("%s",s); n=strlen(s);
lq=qread();
for (int i=;i<=lq;i++)
{
kk[i]=qread();
scanf("%s",t); ll[i]=strlen(t);
ques[ac.insert(t,i)]=i;
} ac.makefail();
ac.buildtree();
ac.pei(s);
bing();
for (int i=;i<=lq;i++) printf("%d\n",ans[i]);
return ;
}

Codeforces963D. Frequency of String的更多相关文章

  1. Codeforces963C Frequency of String 【字符串】【AC自动机】

    题目大意: 给一个串s和很多模式串,对每个模式串求s的一个最短的子串使得这个子串中包含至少k个该模式串. 题目分析: 均摊分析,有sqrt(n)种长度不同的模式串,所以有关的串只有msqrt(n)种. ...

  2. CodeForces - 963D:Frequency of String (bitset暴力搞)

    You are given a string ss. You should answer nn queries. The ii-th query consists of integer kiki an ...

  3. CF963D Frequency of String

    https://codeforces.com/problemset/problem/123/D 题目大意 给一个字符串 \(s\),每次询问一个字符串 \(m_i\) 和一个正整数 \(k_i\),问 ...

  4. Tinkoff Internship Warmup Round 2018 and Codeforces Round #475 (Div. 1)D. Frequency of String

    题意:有一个串s,n个串模式串t,问s的子串中长度最小的包含t k次的长度是多少 题解:把所有t建ac自动机,把s在ac自动机上匹配.保存每个模式串在s中出现的位置.这里由于t两两不同最多只有xsqr ...

  5. Frequency of String CodeForces - 963D

    http://codeforces.com/contest/963/problem/D 题解:https://www.cnblogs.com/Blue233333/p/8881614.html 记M为 ...

  6. 利用JAVA计算TFIDF和Cosine相似度-学习版本

    写在前面的话,既然是学习版本,那么就不是一个好用的工程实现版本,整套代码全部使用List进行匹配效率可想而知. [原文转自]:http://computergodzilla.blogspot.com/ ...

  7. Chp17: Moderate

    17.1 swap a number in place.(without temporary variables) a = a ^ b; b = a ^ b; a = a ^ b; 17.3 Writ ...

  8. 《Algorithms 4th Edition》读书笔记——3.1 符号表(Elementary Symbol Tables)-Ⅲ

    3.1.3 用例举例 在学习它的实现之前我们还是应该先看看如何使用它.相应的我们这里考察两个用例:一个用来跟踪算法在小规模输入下的行为测试用例和一个来寻找更高效的实现的性能测试用例. 3.1.3.1 ...

  9. Jason Wang: 结对编程 CountWord(第三次作业)

    本次作业地址: https://edu.cnblogs.com/campus/xnsy/SoftwareEngineeringClass1/homework/2882 学号: 201731072323 ...

随机推荐

  1. halcon相机标定及图像矫正

    https://blog.csdn.net/humanking7/article/details/44756073 相机标定内容详解:转载自 祥的博客 预备知识 标定中的四个坐标系 1.1.平面旋转 ...

  2. select *from where 和select *from jion on 语句的差别

    https://zhidao.baidu.com/question/541791438.html select 学号 a,成绩 a,姓名 b from 成绩表 a,学生表 b where a.学号=b ...

  3. iOS的设计备忘录/资源集合(新手快速开发)

    iOS的设计备忘录 随着iOS7更新,风格走上扁平化,大部分iOS设计师及程序员都需要对自己的软件做相关调整,尺寸.Icon.UI等等,我在这里总结一下相关资料,以及提供一些关于iOS7设计素材. 一 ...

  4. javascript基本数据类型问题汇总

    isNaN()检测是否是NaN: 比较浮点相等,用绝对值,是否小于某一个阈值 Math.abs(1/3 - (1-2/3))<0.0000001: 字符串多行显示\n,ES6中使用反引号``: ...

  5. cocos2d popSceneWithTransition()方法

    要在CCDirector.h中增加如下方法: template <typename T> void popSceneWithTransition(float t) { CCASSERT(_ ...

  6. CF-1111 (2019/2/7 补)

    CF-1111 题目链接 A. Superhero Transformation tags : strings #include <bits/stdc++.h> using namespa ...

  7. [图文] Fedora 28 使用 Virt-Manager 制作并优化QCOW2镜像——Windows 10 1709

    实验说明: 云计算的发展使得桌面上云,windows 10就必不可少,这一章就如何制作QCOW2镜像文件并优化进行说明. 实验环境: 宿主机系统   :Fedora 28 WorkStation 虚拟 ...

  8. perl中foreach(一)

    perl中的foreach结构  首先语法 foreach $rock(qw /bedrock slate lava/){        $rock="\t$rock";      ...

  9. 【css】清楚浏览器端缓存

    /css/common.css?version=1.0.7   在css链接后面加个参数版本号控制,刷新浏览器缓存

  10. Java基础知识:集合框架

    *本文是最近学习到的知识的记录以及分享,算不上原创. *参考文献见链接. 目录 集合框架 Collection接口 Map接口 集合的工具类 这篇文章只大致回顾一下Java的总体框架. 集合框架 ht ...