【BZOJ4300】 绝世好题
傻逼题都不能一眼看出思路……
原题:
给定一个长度为n的数列ai,求ai的子序列bi的最长长度,满足bi&bi-1!=0(2<=i<=len)。
n<=100000,ai<=2*10^9
这道题我第一眼看诶,这样是不是只需要搞一个计数,如果满足条件计数+1,不满足就清零(实际上是变为1),最后取最大不就好了?
交上去wa了,去uoj群里和dalao讨论发现求的是子序列……
就是说不要求连续
这个好像就有点难搞了?但是我之前为了确定是不是题意有误去搜了题解,已经get到了按位处理的思路
每次读入一个数,每一位如果&上次的这一位不为0,这一位的f就++并更新最大值,所有位都扫完后把所有和上次&不为0的位上的f设为最大值就好辣
感觉这个做法我还是要想一段时间啊
经验还要提高
1 #include<iostream> 2 #include<cstdio> 3 #include<algorithm> 4 #include<cstring> 5 #include<cmath> 6 #include<vector> 7 using namespace std; 8 int rd(){int z=0,mk=1; char ch=getchar(); 9 while(ch<'0'||ch>'9'){if(ch=='-')mk=-1; ch=getchar();} 10 while(ch>='0'&&ch<='9'){z=(z<<3)+(z<<1)+ch-'0'; ch=getchar();} 11 return z*mk; 12 } 13 int n,a; 14 int f[31]; 15 int main(){//freopen("ddd.in","r",stdin); 16 cin>>n; 17 int maxx; 18 for(int i=1;i<=n;++i){ 19 a=rd(); maxx=0; 20 for(int j=0;j<=30 && (1<<j)<=a;++j)if((1<<j)&a) maxx=max(maxx,f[j]+1); 21 for(int j=0;j<=30 && (1<<j)<=a;++j)if((1<<j)&a) f[j]=maxx; 22 } 23 maxx=0; 24 for(int i=0;i<=30;++i) maxx=max(maxx,f[i]); 25 cout<<maxx<<endl; 26 return 0; 27 }