这题说的找出一个数组串 3等分 第一个部分和第3个部分一样,第二个部分和第一个部分回文,那么计算出这些字符串问这样的字符串最长为多少,我们先使用manacher 计算出每个位置以他为对称轴左边端点的最长回文半径 加入第i个位置 回文半径为 d[i],那么他能影响的范围为d[i]-i至i 如果他是那个最大的那么答案就是 i-j (j为[d[i]-i,i]之间的数),我们可以再适当的点加入这个位置的影响在线段树中,然后在最后使用线段树查找出这个区间的最值是多少

#include <iostream>
#include <algorithm>
#include <cstdio>
#include <string.h>
#include <vector>
using namespace std;
const int maxn=;
int str[maxn];
int s[maxn*];
int rad[maxn*];//以i为中心的回文串 半径
int H[maxn],to[maxn],nx[maxn],numofedg;
int d[maxn];
void addedg(int u, int v)
{
++numofedg; to[numofedg]=v; nx[numofedg]=H[u]; H[u]=numofedg;
}
void manacher(int len)
{ int cur=;
s[]=-;
for(int i=; i<len; i++)
{
s[cur++]=str[i];
s[cur++]=-;
}
rad[]=;
int id=;
for(int i=; i<cur; i++)
{
if(rad[id]+id>i)rad[i]=min(rad[*id-i],rad[id]+id-i);
else rad[i]=;
while(i-rad[i]>=&&i+rad[i]<cur&&s[ i - rad[i] ] == s[ i+rad[i] ])rad[i]++;
if(id+rad[i]<i+rad[i])id=i;
}
for(int i=; i<=len; i++)
{
d[i]=rad[i*]/;
if(d[i]==)continue;
addedg(i-d[i],i);
} }
struct Itree
{
int loc,cL,cR,ans;
int val[maxn*];
void build(int L, int R, int o)
{
val[o]=;
if(L==R) return ;
int mid=(L+R)>>;
build(L,mid,o*);
build(mid+,R,o*+);
}
void update(int L, int R, int o)
{
if(L==R)
{
val[o]=L ; return ;
}
int mid=(L+R)>>;
if(loc<=mid) update(L,mid,o*);
else update(mid+,R,o*+);
val[o]=max(val[o*],val[o*+]);
}
void query(int L, int R, int o)
{
if(cL<=L&&R<=cR)
{
ans=max(ans,val[o]); return;
}
int mid=(L+R)>>;
if(cL<=mid)query(L,mid,o*);
if(cR>mid) query(mid+,R,o*+);
}
}T;
int main()
{
int cas;
scanf("%d",&cas); for(int cc=; cc<=cas; cc++)
{
int n;
scanf("%d",&n);
H[]=;numofedg=;
for(int i=; i<n; i++){
H[i+]=;
scanf("%d",&str[i]);
}
manacher(n);
int ans=;
T.build(,n,);
d[]=;
for(int i=; i<n; i++)
{
for(int j=H[i]; j; j=nx[j])
{
T.loc=to[j]; T.update(,n,);
}
T.cL=i+;T.cR=d[i]+i;
if(T.cL>T.cR)continue;
T.ans=;
T.query(,n,);
ans=max(ans,T.ans-i);
}
printf("Case #%d: %d\n",cc,ans*);
}
return ;
}

hdu5371 manacher + 线段树的更多相关文章

  1. bzoj 2565: 最长双回文串【manacher+线段树】

    因为我很愚蠢所以用了很愚蠢的O(nlogn)的manacher+线段树做法 就是开两个线段树mn和mx分别表示左端点在i的最长回文子串和右端点在i的最长回文子串 用manacher求出每个点的最长回文 ...

  2. 洛谷P4555 [国家集训队]最长双回文串(manacher 线段树)

    题意 题目链接 Sol 我的做法比较naive..首先manacher预处理出以每个位置为中心的回文串的长度.然后枚举一个中间位置,现在要考虑的就是能覆盖到i - 1的回文串中 中心最靠左的,和能覆盖 ...

  3. 计蒜之道 初赛 第三场 题解 Manacher o(n)求最长公共回文串 线段树

    腾讯手机地图 腾讯手机地图的定位功能用到了用户手机的多种信号,这当中有的信号的作用范围近.有的信号作用的范围则远一些.有的信号相对于用户在不同的方位强度是不同的,有的则是在不论什么一个方向上信号强度都 ...

  4. 牛客练习赛64 如果我让你查回文你还爱我吗 线段树 树状数组 manacher 计数 区间本质不同回文串个数

    LINK:如果我让你查回文你还爱我吗 了解到了这个模板题. 果然我不会写2333... 考试的时候想到了一个非常辣鸡的 线段树合并+莫队的做法 过不了不再赘述. 当然也想到了manacher不过不太会 ...

  5. bzoj3932--可持久化线段树

    题目大意: 最近实验室正在为其管理的超级计算机编制一套任务管理系统,而你被安排完成其中的查询部分.超级计算机中的 任务用三元组(Si,Ei,Pi)描述,(Si,Ei,Pi)表示任务从第Si秒开始,在第 ...

  6. codevs 1082 线段树练习 3(区间维护)

    codevs 1082 线段树练习 3  时间限制: 3 s  空间限制: 128000 KB  题目等级 : 大师 Master 题目描述 Description 给你N个数,有两种操作: 1:给区 ...

  7. codevs 1576 最长上升子序列的线段树优化

    题目:codevs 1576 最长严格上升子序列 链接:http://codevs.cn/problem/1576/ 优化的地方是 1到i-1 中最大的 f[j]值,并且A[j]<A[i] .根 ...

  8. codevs 1080 线段树点修改

    先来介绍一下线段树. 线段树是一个把线段,或者说一个区间储存在二叉树中.如图所示的就是一棵线段树,它维护一个区间的和. 蓝色数字的是线段树的节点在数组中的位置,它表示的区间已经在图上标出,它的值就是这 ...

  9. codevs 1082 线段树区间求和

    codevs 1082 线段树练习3 链接:http://codevs.cn/problem/1082/ sumv是维护求和的线段树,addv是标记这歌节点所在区间还需要加上的值. 我的线段树写法在运 ...

随机推荐

  1. 转:Eclipse 各种小图标的含义

    原文地址:https://www.cnblogs.com/widget90/p/7592507.html Eclipse 各种小图标的含义,记录一下. Eclipse的Package Explorer ...

  2. MAC终端TAB自动补全忽略大小写

    打开终端,输入: nano .inputrc 在里面粘贴上以下语句: set completion-ignore-case onset show-all-if-ambiguous onTAB: men ...

  3. 使用IntelliJ IDEA创建Maven聚合工程、创建resources文件夹、ssm框架整合、项目运行一体化

    一.创建一个空的项目作为存放整个项目的路径 1.选择 File——>new——>Project ——>Empty Project 2.WorkspaceforTest为项目存放文件夹 ...

  4. php中$this->的用法简单介绍

    php中我们一般是先声明一个类,然后用这个类去实例化对象!$this 的含义是表示实例化后的具体对象!$this->表示在类本身内部使用本类的属性或者方法.‘->’符号是“插入式解引用操作 ...

  5. mysql开发总结

    一.理解MySQL基本概念 1.MySQL软件:MySQL实际上就是一软件,是一工具,是关系型数据库管理系统软件 2.MySQL数据库:就是按照数据结构来组织.存储和管理数据的仓库 3.MySQL数据 ...

  6. Python3学习之路~5.2 time & datetime模块

    time模块 时间相关的操作,时间有三种表示方式: 时间戳               1970年1月1日之后的秒,即:time.time() 格式化的字符串    2014-11-11 11:11, ...

  7. 封装||property

    封装 封装:主要是指在类的定义阶段将,以__开头的属性名进行变形..例如:__name ==> _People__name 封装的主要特点: 1.在类外部无法直接__name,想要在外部调用可以 ...

  8. C语言ini格式配置文件的读写

    依赖的类 /*1 utils.h *# A variety of utility functions. *# *# Some of the functions are duplicates of we ...

  9. 实习培训——Java异常处理(8)

    实习培训——Java异常处理(8) Java 异常处理 异常是程序中的一些错误,但并不是所有的错误都是异常,并且错误有时候是可以避免的. 比如说,你的代码少了一个分号,那么运行出来结果是提示是错误 j ...

  10. 银联卡中关于CVN/CVN2/ICVN的区别

    银联China Union Pay,是中国唯一合法的卡组织机构,同时也是EMVCo成员.关于银联卡中CVN/CVN2/ICVN的区别,刚开始我自己不了解,但经过查找资料和请教其他人,对它们的概念也渐渐 ...