hdu4521(最长递增子序列的二分思想)

题意:就是求一个序列的最长递增子序列,但是下标有要求就是新的序列的相邻项的下标相差d.

思路:在原来求最长递增子序列的基础上加一些条件使得相邻项的下标相差d....

代码实现:

#include<stdio.h>
#include<string.h>
int a[100005],dp[100005],b[100005];
int main()
{
   int n,d,i,temp;
   while(scanf("%d%d",&n,&d)!=EOF)
   {
       int p,r,m,len=1,max=1;
       for(i=0;i<n;i++)
       {
           scanf("%d",&a[i]);
           b[i]=100000000;
       }
       b[0]=-100000000;b[1]=a[0];b[n]=100000000;
       for(i=0;i<=d;i++)
           dp[i]=1;
       for(i=d+1;i<n;i++)
       {
          p=0,r=len;
          while(p<=r)//二分求a[i]在序列中的位置
          {  
              m=(p+r)/2;
              if(a[i]>b[m])
                  p=m+1;
              else
                  r=m-1;
          }
          temp=i-d;//这个东西的设置很重要的,就是需要看a[i-d]能否放入新的序列,就是比原来的小
          dp[i]=p;
          if(b[dp[temp]]>a[temp])
          {
              if(b[dp[temp]]==100000000)//此时需要长度加1
                 len++;
              b[dp[temp]]=a[temp];      
          }
          if(dp[i]>max)
              max=dp[i];
       }
       printf("%d\n",max);
   }
   return 0;
}
原文地址:https://www.cnblogs.com/jiangjing/p/2983670.html