您的位置:首页 > 其它

最小(大)表示法习题 -- 来自[kuangbin带你飞]专题十六 KMP & 扩展KMP & Manacher

2016-02-22 08:43 471 查看
习题地址:


http://vjudge.net/contest/70325#overview


o.

题意:每组一个字符串,eof结束。求最小和最大表示法的位置,以及最小最大串出现的次数

做法:先求出最小位置和最大位置。最大位置只需增加代码当s[(i +k)%n] >
s[(j +k)%n].j发生变化。反之i变化即可。第二步获得nexta数组。得到最小循环串n-nexta
判断该字符串是否是周期的,如果是周期的,最小和最大的位置就是周期出现的次数

#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
using namespace std;
int nexta[1000002];
char s[1000002];
int n;
void getnexta()
{
memset(nexta,0,sizeof(nexta));
int k = -1,j = 0;
nexta[0] = -1;
while(j < n )
{

if(k == -1 || s[k] == s[j])
{
nexta[j + 1] = k + 1;
j ++;
k ++;
}
else
{
k = nexta[k];
}
}
}
int minandmax(int x)
{
int i = 0,j = 1,k = 0;
int t;
while(i < n && j < n && k < n)
{
t = s[(i + k) % n] - s[(j + k) %n];
if(t == 0)
{
k ++;
}
else
{
if(x == 0)
{
if(t > 0)
{
i = i + k + 1;
}
else
{
j = j + k + 1;
}
}
else
{
if(t < 0)
{
i = i + k + 1;
}
else
{
j = j + k + 1;
}
}
if(i == j)
{
j ++;
}
k = 0;
}

}
return min(i,j);
}
int main()
{
//freopen("in.txt","r",stdin);
int maxx,minx,ans;
while(scanf("%s",s) != EOF)
{
n = strlen(s);
getnexta();
minx = minandmax(0) + 1;
maxx = minandmax(1) + 1;
if(n % (n -nexta
) == 0)
{
ans = n / (n -nexta
);
}
else
ans = 1;
printf("%d %d %d %d\n",minx,ans,maxx,ans);
}

return 0;
}
//bcabcabca bca bca bca
p.

题意:每组数据n个0,1字符串。判断这些是由几种字符串第一个字符移动到最后的位置构成的

做法:求出每一个字符串的最小表示法,判断不同的字符串有几个

#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
#include <map>
using namespace std;
map<string,int>mapp;
char s[102],t[102];
int n;
int getmin()
{
int i = 0,j = 1,k = 0;
int t;
while(i < n && j < n && k < n)
{
t = s[(i + k) % n] - s[(j + k) %n];
if(t == 0)
{
k ++;
}
else
{
if(t > 0)
{
i = i + k + 1;
}
else
{
j = j + k + 1;
}

if(i == j)
{
j ++;
}
k = 0;
}

}

return min(i,j);
}
int main()
{
//freopen("in.txt","r",stdin);
int m,a,ans;
string p;
while(scanf("%d",&m)!= EOF)
{
mapp.clear();
for(int i = 0; i < m; i ++)
{

scanf("%s",s);
n = strlen(s);
a = getmin();
for(int j = 0; j < n; j ++)
{
t[j] = s[(a + j) % n];
}
t
= '\0';
p = t;
mapp[p] ++;
}

ans = mapp.size();
printf("%d\n",ans);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: