ural 1297
来源:互联网 发布:排施工计划软件 编辑:程序博客网 时间:2024/06/18 11:12
题意:求一个字符串的最长回文子串,有多个相同长度时输出最先出现的那个。
对这道题,刚开始得到的一个提示是在原串后面加一个不可能出现的字符,再把原串反转拼接到后面,接着求由不可能出现字符分开的两部分的最长公共前缀。后来这样试了一下,很明显的就WA了,像abfeba这种数据会输出ab,很明显不行。于是看了题解,才明白。。。。
正确的应该是枚举原串的每个字符,将其作为回文中心,当枚举到i时,分奇偶求两次,偶数求height[i+1]和height[len-i-1]的最长公共前缀,奇数时求height[i]和height[len-i-1]的最长公共前缀,取所有结果里最大的就行了。(len是拼接后字符串长度)
代码如下:
#include <cstdio>#include <stack>#include <set>#include <iostream>#include <string>#include <vector>#include <queue>#include <list>#include <functional>#include <cstring>#include <algorithm>#include <cctype>#include <string>#include <map>#include <iomanip>#include <cmath>#define LL long long#define ULL unsigned long long#define SZ(x) (int)x.size()#define MP(a, b) make_pair(a, b)#define MS(arr, num) memset(arr, num, sizeof(arr))#define PB push_back#define F first#define S second#define ROP freopen("input.txt", "r", stdin);#define MID(a, b) (a + ((b - a) >> 1))#define lson l,mid,rt<<1#define rson mid+1,r,rt<<1|1#define lrt rt << 1#define rrt rt << 1|1#define root 1,n,1#define BitCount(x) __builtin_popcount(x)#define BitCountll(x) __builtin_popcountll(x)#define LeftPos(x) 32 - __builtin_clz(x) - 1#define LeftPosll(x) 64 - __builtin_clzll(x) - 1const double PI = acos(-1.0);const int INF = 1e7;using namespace std;const double eps = 1e-5;const int MAXN = 300 + 10;const int MOD = 1000007;const double M=1e-8;const int N=2100;typedef pair<int, int> pii;typedef pair<int, string> pis;int m,sa[N],rank[N],height[N],dp[N][N];int wa[N],wb[N],wv[N], cnt[N];bool cmp(int *y,int a,int b,int l){ return y[a]==y[b] && y[a+l]==y[b+l];}void da(char s[],int n,int m){ int i,j,p,*x=wa,*y=wb; MS(cnt,0); for (i=0;i<n;i++) cnt[x[i]=s[i]]++; for (i=1;i<m;i++) cnt[i]+=cnt[i-1]; for (i=n-1;i>=0;i--) sa[--cnt[x[i]]]=i; for (j=1,p=1;p<n;j<<=1,m=p) { for (p=0,i=n-j;i<n;i++) y[p++]=i; for (i=0;i<n;i++) if (sa[i]>=j) y[p++]=sa[i]-j; for (i=0;i<n;i++) wv[i]=x[y[i]]; MS(cnt,0); for (i=0;i<n;i++) cnt[wv[i]]++; for (i=1;i<m;i++) cnt[i]+=cnt[i-1]; for (i=n-1;i>=0;i--) sa[--cnt[wv[i]]]=y[i]; swap(x,y); for (i=1,p=1,x[sa[0]]=0;i<n;i++) { x[sa[i]]=cmp(y,sa[i],sa[i-1],j)?p-1:p++; } }}void getHeight(char s[],int n){ int i,j,k=0; for (i=1;i<=n;i++) rank[sa[i]]=i; for (i=0;i<n;height[rank[i++]]=k) { for (k?k--:0,j=sa[rank[i]-1];s[i+k]==s[j+k];k++) ; }}void rmq(int n){ int i,j,k=log(n)/log(2); for (i=1;i<=n;i++) dp[i][0]=height[i]; for (j=1;j<=k;j++) for (i=1;i+(1<<j)-1<=n;i++) { dp[i][j]=min(dp[i][j-1],dp[i+(1<<(j-1))][j-1]); }}int query(int x,int y){ int k=log(y-x+1)/log(2); return min(dp[x][k],dp[y-(1<<k)+1][k]);}int lcp(int x,int y){ int l=rank[x],r=rank[y]; if (l>r) swap(l,r); l++; return query(l,r);}char s[N],r[N];int n;void slove(){ int i,j,mx1=-INF,mx2=-INF,p1,p2,p; for (i=0;i<n/2;i++) { // 奇数时 int t=lcp(i,n-i-1); if (t>mx1) mx1=t,p1=i; } for (i=0;i<n/2-1;i++) { // 偶数时 int t=lcp(i+1,n-i-1); if (t>mx2) mx2=t,p2=i; } int len; if (mx2*2>mx1*2-1) { // 求最大长度 len=mx2*2; p1=p2,mx1=mx2; } else { len=mx1*2-1; } //cout<<p1-mx1+1<<" "<<len<<endl; len+=p1-mx1+1; for (i=p1-mx1+1;i<len;i++) putchar(s[i]); puts("");}int main(){ int i,j; while(~scanf("%s",s)) { n=strlen(s); r[0]='\0'; strcat(r,s); reverse(r,r+n); s[n]='|',s[n+1]='\0'; strcat(s,r); n=strlen(s); s[n]=0; da(s,n+1,128); getHeight(s,n); rmq(n);// for (i=1;i<=n;i++) cout<<sa[i]<<" "; cout<<endl;// for (i=0;i<n;i++) cout<<rank[i]<<" "; cout<<endl;// for (i=1;i<=n;i++) cout<<height[i]<<" "; cout<<endl; slove(); }}/*descramblerwillchoosethetextscanningdirectionatrandomabfeba*/
0 0
- URAL 1297
- ural 1297
- ural 1297
- URAL 1297
- 【回文串】ural 1297
- ural 1297 Palindrome
- Ural-1297-Palindrome
- URAL 1297 Palindrome
- URAL 1297 Palindrome
- URAL 1297Palindrome
- URAL 1297 Palindrome
- URAL
- 【ural】
- URAL
- URAL
- URAL
- URAL
- URAL
- HDU 5353 Average(贪心)
- 【codechef】Chef and the Cards(dp,推论)
- java项目转成WEB项目快捷方法
- [C++11 并发编程] 16 在期望中保存异常
- 虚拟机使用同一镜像做NLB测试失败的问题
- ural 1297
- Thinking in Java---线程通信+三种方式实现生产者消费者问题
- ecplise中tomcat插件
- 利用javadoc生成API文档
- POJ 2777 Count Color(位运算+线段树+lazy+区间更新)
- 网站前端技术学习 笔记
- allegro不规则焊盘制作
- 链栈的学习(回文数)
- 小马哥----高仿小米4 主板型号M168 拆机刷机机型图与开机界面识别图 多图展示