洛谷P1439 最长公共子序列(LCS问题)
2017-11-01 15:31
281 查看
DP
题目传送门一般LCS做法是O(n2)的,但是这道题数据范围有1e5,因此必须另辟蹊径
注意到两个数列是n的一个排列,因此考虑把第一个数列中数的位置给记录下来,再根据这个记录第二个数列的位置。然后就转化成了LIS问题,用O(nlog2n)来实现即可。
讲的不是很清楚啊。。。具体看代码吧。。。
代码:
#include<cstdio> #include<cstring> #include<algorithm> #define MAXN 100000 using namespace std; int n,t; int g[MAXN+5],f[MAXN+5],a[MAXN+5],b[MAXN+5],c[MAXN+5]; inline char readc(){ static char buf[100000],*l=buf,*r=buf; if (l==r) r=(l=buf)+fread(buf,1,100000,stdin); if (l==r) return EOF; return *l++; } inline int _read(){ int num=0; char ch=readc(); while (ch<'0'||ch>'9') ch=readc(); while (ch>='0'&&ch<='9') { num=num*10+ch-48; ch=readc(); } return num; } int erfen(int v){ int l=1,r=t; while (l<=r){ int mid=(l+r)/2; if (v>g[mid]) l=mid+1; else r=mid-1; } return l; } int main(){ n=_read(); for (int i=1;i<=n;i++) a[i]=_read(),f[a[i]]=i;//记录位置 for (int i=1;i<=n;i++) b[i]=_read(),c[i]=f[b[i]];//根据上次的记录来记录 g[++t]=c[1]; for (int i=2;i<=n;i++)//LIS if (c[i]>g[t]) g[++t]=c[i]; else g[erfen(c[i])]=c[i]; printf("%d\n",t); }
相关文章推荐
- 洛谷P1439 最长公共子序列(LCS问题)
- 洛谷 P1439 排列LCS问题
- xjb——洛谷 P1439 排列LCS问题
- 洛谷 P1439 排列LCS问题
- 洛谷 P1439 排列LCS问题
- 洛谷P1439 排列LCS问题
- 洛谷P1439 排列LCS问题
- 最长公共子序列LCS问题
- 最长公共子序列(LCS)问题(非连续子序列)的两种解法
- 最长公共子序列(LCS)问题
- 动态规划经典问题---最长公共子序列(LCS)
- 求解最长公共子序列问题(LCS)
- 最长公共子序列(LCS)问题
- 最长公共子序列问题LCS
- 动态规划解决最长公共子序列LCS问题
- 算法导论,动态规划 —— 最长公共子序列问题(LCS)优化python示例
- DP复习——最长公共子序列 LCS 问题
- 最长公共子序列问题(LCS)
- 最长公共子序列(LCS)问题
- 最长公共子序列问题(LCS) - 动态规划