[Poi2012]A Horrible Poem BZOJ2795

news/2024/6/17 1:49:29

分析:

这是今天下午的考试题,推了2个小时,考试中A掉了

首先,循环串通过字符串hash可以O(1)判断:get_hash(l,r-len)==get_hash(l+len,r);显然可证。

我们其次可以发现,循环串的长度是所求串的长度的约数

之后我们可以发现,如果两个不同的子串是循环串,那么这两个子串长度的gcd也一定是循环串。

那么,我们就可以发现,将长度质因数分解,之后每次判断长度/这个质因子的所得长度能否构成循环串,如果能,就将长度除以这个质因子。

至于质因子,我们可以线筛...详情自己去分析,或者去看下面的代码...懒得讲了...

附上代码:

#include <cstdio>
#include <cmath>
#include <iostream>
#include <queue>
#include <algorithm>
#include <cstring>
#include <cstdlib>
using namespace std;
#define N 500005
#define Base 131
#define ll unsigned long long
char s[N];
ll hash[N],b[N];
int n,Q,ans[N],pri[N],vis[N],last[N],cnt;
ll get_hash(int x,int y)
{
	return hash[y]-hash[x-1]*b[y-x+1];
}
void init()
{
	for(int i=2;i<=n;i++)
	{
		if(!vis[i])
		{
			pri[++cnt]=i;
			last[i]=i;
		}
		for(int j=1;j<=cnt&&i*pri[j]<=n;j++)
		{
			vis[pri[j]*i]=1;last[pri[j]*i]=pri[j];
			if(!(i%pri[j]))break;
		}
	}
}
int que[N];
int main()
{
	//freopen("str.in","r",stdin);
	//freopen("str.out","w",stdout);
	scanf("%d",&n);
	init();
	scanf("%s",s+1);
	b[0]=1;
	for(int i=1;i<=n;i++)b[i]=b[i-1]*Base;
	for(int i=1;i<=n;i++)
	{
		hash[i]=hash[i-1]*Base+s[i]-'a';
	}
	scanf("%d",&Q);
	while(Q--)
	{
		int a,b;
		scanf("%d%d",&a,&b);
		int len=b-a+1;int t=len,tot=0;
		if(len==1)
		{
			puts("1");
			continue;
		}
		while(t!=1)
		{
			que[++tot]=last[t];
			t=t/last[t];
		}
		for(int i=1;i<=tot;i++)
		{
			t=len/que[i];
			if(get_hash(a,b-t)==get_hash(a+t,b))len=len/que[i];
		}
		printf("%d\n",len);
	}
	return 0;
}

Orz O(n*sqrt(n))的时间也能过...暴力踩标程...

转载于:https://www.cnblogs.com/Winniechen/p/9042992.html


http://www.niftyadmin.cn/n/1662856.html

相关文章

线程同步之信号量

什么是信号量 信号量&#xff08;semaphore&#xff09;是操作系统用来解决并发中的互斥和同步问题的一种方法。与互斥量不同的地方是&#xff0c;它允许多个线程在同一时刻访问同一资源&#xff0c;但是需要限制在同一时刻访问此资源的最大线程数目。 信号量的工作原理以一个…

深入理解内核对象与函数句柄

1. 内核对象 Windows中每个内核对象都只是一个内存块&#xff0c;它由操作系统内核分配&#xff0c;并只能由操作系统内核进行访问&#xff0c;应用程序不能在内存中定位这些数据结构并直接更改其内容。这个内存块是一个数据结构&#xff0c;其成员维护着与对象相关的信息。少…

【Vue.js学习笔记】11:组件中CSS的作用域

样式表最终的生成位置 有两个组件&#xff0c;一个是根组件App&#xff0c;一个是子组件Users。它们都有一个h2标签&#xff0c;先只在根组件上写CSS样式。 App.vue <template><div id"app"><h2>父组件的h2标签</h2></div> </te…

topcoder srm 565 div1

problem1 link $f[i][j]$表示经过前$i$个怪物之后&#xff0c;花费$j$个硬币可以得到的最大值。 problem2 link 设$nim[i]$表示数字$i$的nim值。那么题目就是求有多少个区间$[L,R]$满足这个区间内所有数字的nim值的抑或不是&#xff10;&#xff0e;通过记录前缀和的个数&#…

Anaconda3环境使用TensorFlow报错解决记录 mistGPU

先上总结 主要是由于代码是基于tensorflow1.0编写的&#xff0c;目前最新的版本是2.0&#xff0c;版本更新比较大&#xff0c;很多方法已经改名&#xff0c;或者弃用。多数报错为 has no attribute xxx 为确保高版本的TF支持低版本的TF代码&#xff0c;升级脚本加入了 compat.…

【Vue.js学习笔记】12:组件嵌套的Demo页面

组件嵌套的Demo页面 这里按照课程视频里所做&#xff0c;将Header和Footer使用相应的语义化标签包装成组件&#xff0c;一起装进根组件中来使用&#xff0c;建立一个小Demo网页。 App.vue <template><div id"app"><app-header></app-header&…

量子计算技术的现状、流派、挑战与前景

作为一个热门概念&#xff0c;我们经常听到量子计算又有新突破的消息。但很少人清楚&#xff0c;今天的量子计算技术究竟走到了哪一步&#xff1f;到底有多少种实现量子计算的方式&#xff1f;本文将对这两个问题进行全面梳理&#xff0c;介绍如今各技术流派的发展&#xff0c;…

进程的通信 - 剪切板

剪切板是系统维护管理的一块内存区域&#xff0c;本机的所有进程都可以访问。当一个进程复制数据时&#xff0c;先将数据放在该内存区&#xff0c;当另一个进程粘贴时&#xff0c;则是从该内存区块取出数据 剪切板操作&#xff1a; 其实在剪切板中也就那几个API在使用&#x…