Stammering Aliens
| Time Limit: 2000MS | Memory Limit: 65536K | |
Description
Thus, the message contains possibly overlapping repetitions of the same words over and over again. As a result, Ellie turns to you, S.R. Hadden, for help in identifying the gist of the message.
Given an integer m, and a string s, representing the message, your task is to find the longest substring of s that appears at least m times. For example, in the message baaaababababbababbab, the length-5 word babab is contained 3 times, namely at positions 5, 7 and 12 (where indices start at zero). No substring appearing 3 or more times is longer (see the first example from the sample input). On the other hand, no substring appears 11 times or more (see example 2). In case there are several solutions, the substring with the rightmost occurrence is preferred (see example 3).
Input
Output
Sample Input
3
baaaababababbababbab
11
baaaababababbababbab
3
cccccc
0
Sample Output
5 12
none
4 2
分析:求出现至少m次的最长字符子串及最大位置;
后缀数组+set;(二分hash)
代码:
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cmath>
#include <algorithm>
#include <climits>
#include <cstring>
#include <string>
#include <set>
#include <map>
#include <unordered_map>
#include <queue>
#include <stack>
#include <vector>
#include <list>
#define rep(i,m,n) for(i=m;i<=n;i++)
#define rsp(it,s) for(set<int>::iterator it=s.begin();it!=s.end();it++)
#define mod 1000000007
#define inf 0x3f3f3f3f
#define vi vector<int>
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define ll long long
#define pi acos(-1.0)
#define pii pair<int,int>
#define Lson L, mid, ls[rt]
#define Rson mid+1, R, rs[rt]
#define sys system("pause")
#define freopen freopen("in.txt","r",stdin)
const int maxn=4e4+;
using namespace std;
ll gcd(ll p,ll q){return q==?p:gcd(q,p%q);}
ll qpow(ll p,ll q){ll f=;while(q){if(q&)f=f*p;p=p*p;q>>=;}return f;}
inline ll read()
{
ll x=;int f=;char ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<=''){x=x*+ch-'';ch=getchar();}
return x*f;
}
int n,m,k,t,cntA[maxn],cntB[maxn],sa[maxn],lev[maxn],height[maxn],A[maxn],B[maxn],tsa[maxn];
char ch[maxn];
void solve()
{
for (int i = ; i < ; i ++) cntA[i] = ;
for (int i = ; i <= n; i ++) cntA[ch[i]] ++;
for (int i = ; i < ; i ++) cntA[i] += cntA[i - ];
for (int i = n; i; i --) sa[cntA[ch[i]] --] = i;
lev[sa[]] = ;
for (int i = ; i <= n; i ++)
{
lev[sa[i]] = lev[sa[i - ]];
if (ch[sa[i]] != ch[sa[i - ]]) lev[sa[i]] ++;
}
for (int l = ; lev[sa[n]] < n; l <<= )
{
for (int i = ; i <= n; i ++) cntA[i] = ;
for (int i = ; i <= n; i ++) cntB[i] = ;
for (int i = ; i <= n; i ++)
{
cntA[A[i] = lev[i]] ++;
cntB[B[i] = (i + l <= n) ? lev[i + l] : ] ++;
}
for (int i = ; i <= n; i ++) cntB[i] += cntB[i - ];
for (int i = n; i; i --) tsa[cntB[B[i]] --] = i;
for (int i = ; i <= n; i ++) cntA[i] += cntA[i - ];
for (int i = n; i; i --) sa[cntA[A[tsa[i]]] --] = tsa[i];
lev[sa[]] = ;
for (int i = ; i <= n; i ++)
{
lev[sa[i]] = lev[sa[i - ]];
if (A[sa[i]] != A[sa[i - ]] || B[sa[i]] != B[sa[i - ]]) lev[sa[i]] ++;
}
}
for (int i = , j = ; i <= n; i ++)
{
if (j) j --;
while (ch[i + j] == ch[sa[lev[i] - ] + j]) j ++;
height[lev[i]] = j;
}
}
multiset<int>p;
set<int>q;
int main()
{
int i,j;
while(~scanf("%d",&m)&&m)
{
scanf("%s",ch+);
n=strlen(ch+);
if(m==)
{
printf("%d %d\n",n,);
continue;
}
solve();
p.clear(),q.clear();
rep(i,,m-)p.insert(height[i]),q.insert(sa[i]);
int ans=,pos=-;
rep(i,m,n)
{
p.erase(p.lower_bound(height[i-m+]));
p.insert(height[i]);
q.insert(sa[i]);
if(ans<=*p.begin())
{
auto x=q.end();
x--;
if(ans<*p.begin()||*x->pos)pos=*x-;
ans=*p.begin();
}
q.erase(sa[i-m+]);
}
if(ans)printf("%d %d\n",ans,pos);
else puts("none");
}
//system("Pause");
return ;
}
Stammering Aliens的更多相关文章
- UVA 12206 - Stammering Aliens(后缀数组)
UVA 12206 - Stammering Aliens 题目链接 题意:给定一个序列,求出出现次数大于m,长度最长的子串的最大下标 思路:后缀数组.搞出height数组后,利用二分去查找就可以 这 ...
- Uva12206 Stammering Aliens 后缀数组&&Hash
Dr. Ellie Arroway has established contact with an extraterrestrial civilization. However, all effort ...
- HDU4080 Stammering Aliens(二分 + 后缀数组)
题目 Source http://acm.hdu.edu.cn/showproblem.php?pid=4080 Description Dr. Ellie Arroway has establish ...
- UVALive - 4513 Stammering Aliens ——(hash+二分 || 后缀数组加二分)
题意:找一个出现了m次的最长子串,以及这时的最右的位置. hash的话代码还是比较好写的,,但是时间比SA多很多.. #include <stdio.h> #include <alg ...
- Hash(LCP) || 后缀数组 LA 4513 Stammering Aliens
题目传送门 题意:训练指南P225 分析:二分寻找长度,用hash值来比较长度为L的字串是否相等. #include <bits/stdc++.h> using namespace std ...
- UVa 12206 (字符串哈希) Stammering Aliens
体验了一把字符串Hash的做法,感觉Hash这种人品算法好神奇. 也许这道题的正解是后缀数组,但Hash做法的优势就是编码复杂度大大降低. #include <cstdio> #inclu ...
- 【HDOJ】4080 Stammering Aliens
1. 题目描述给定一个长为$n \in [1, 4000]$的字符串,求其中长度最长的子串,并且该子串在原串中出现至少$m$次,并求最右起始位置. 2. 基本思路两种方法:二分+后缀数组,或者二分+哈 ...
- uvalive 4513 Stammering Aliens
题意:给你一个串,问期中至少出现m次的最长子串及其起始位置的坐标. 思路:hash+LCP+二分答案 #include<cstdio> #include<cstring> #i ...
- uva 12206 - Stammering Aliens
基于hash的LCP算法: #include<cstdio> #include<cstring> #include<algorithm> #define maxn ...
随机推荐
- .Net使用JsonSchema验证Json
最近项目中遇到了这样的需求,需要对上传的Json进行验证,以确保Json数据的准确性.前后使用了两种方式来验证: (1)第一种方式的实现思想:根据Json数据的格式,严格定义相应的类结构,并在Syst ...
- cmusphinx格式问题
在windows下.lm和.dict同时为ANSI编码,输出正确,否则输出乱码或不输出结果.
- Date Math SimpleDateFormat 类
Date 和 SimpleDateFormat /* Date 日期类 许多方法都被Calendar取代了 Date() 获取当前时间 使用概率最高 Calendar 类用常量获取当前时间 一般很少 ...
- ADO.NET 完整修改、删除、防字符串攻击
首先,我先把昨天所做的人事管理系统进行了优化,将其完善成为了一个更符合实际的系统.将修改及删除数据的数据库操作前面添加了一个查询语句,这样,在实际操作时,如果数据库中没有该条数据,则程序不会执行接下来 ...
- Python 学习笔记5
Life is like a box of chocolate. 今天继续学习Python数据结构. http://www.pythondoc.com/pythontutorial3/datastru ...
- unity 退到桌面的 OnApplicationPause
void OnApplicationFocus( bool isFocus ) { // Debug.Log("--------OnApplicationPause---" + i ...
- libPods.a 无法找到的解决方法
http://stackoverflow.com/questions/9863836/library-not-found-for-lpods To be clear for newbies out t ...
- iOS 加载本地的html文件
方法1: self.webView = [[UIWebView alloc]initWithFrame:self.view.bounds]; NSString *path = [[NSBundle ...
- 12c 补丁架构 以及opatch 功能
cd $ORACLE_HOME/ccr/bin ./emocmrsp oracle@qc550705:/oracle/app/oracle/product/12.1.0.2/db_1/ccr/bin& ...
- JPA 系列教程15-继承-一个表-SINGLE_TABLE
继承映射策略 一个类继承结构一个表的策略,最终只生成一个表,这是继承映射的默认策略. 举例 如果实体类Teacher继承实体类Person,实体类Student也继承自实体Person,那么只会映射成 ...