[AHOI2006] 基因匹配 Match

题目链接http://www.lydsy.com/JudgeOnline/problem.php?id=1264

分析:

这个题拿到手时完全蒙蔽,写了个朴素的LCS果断TLE,后来看了某犇的博客,才知道有利用题目性质用树状数组做的方法。

这两天看了LCS问题转化为LIS问题的模型,想了一发:

对于每个在A串中的基因,在B中必然只有5个匹配点,所以如果转化成LIS,N只会变为原来5倍,即5*10^5,用O(nlogn)的LIS完全能跑过!

代码:

/**************************************************************
    Problem: 1264
    User: Krew
    Language: C++
    Result: Accepted
    Time:472 ms
    Memory:10588 kb
****************************************************************/
 
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <vector>
 
#define rep(i,x,y) for (int i=x;i<=y;i++)
#define dep(i,y,x) for (int i=y;i>=x;i--)
#define read(x) scanf("%d",&x)
 
using namespace std;
 
const int maxn=100000+23,INF=(1<<30);
 
int ans,N,n,rear,k,a[maxn*5],p[maxn*5],g[maxn*5],d[maxn*5];
 
vector<int> s[maxn]; 
 
int main()
{
  read(N);
  n=5*N;
  rep(i,1,n) 
    read(a[i]);
   
  rep(i,1,n) 
  {
    read(k);
    s[k].push_back(i);
  }
   
  rep(i,1,N)
    sort(s[k].begin(),s[k].end());
   
  rear=0;
 
  rep(i,1,n)
    dep(j,4,0) //只有5个匹配
      p[++rear]=s[a[i]][j];
   
  ans=0;
   
  rep(i,0,rear) g[i]=INF;
   
  rep(i,1,rear) //LIS
  {
    int l=lower_bound(g+1,g+rear+1,p[i])-g;
    d[i]=l;
    g[l]=p[i];
    ans=max(ans,d[i]);
  }
   
  printf("%d\n",ans);
   
  return 0;
}


好像不是很快……但是也比较好写吧……

posted @ 2016-04-06 22:57  Krew  阅读(293)  评论(0编辑  收藏  举报