https://ac.nowcoder.com/acm/problem/20860
思路:
要想让异或之后的结果最大,肯定从高位开始就要尽量大,也就是两个数的高位尽量不同。
如果lr的二进制位数不同,首先高位补0补齐,然后看我们能否在r的最高位取1的时候r的最高是不是不一样(如果一样,那么这一位只能取这个值,异或之后就消掉了),一直到第一个不一样的位置,肯定是r的这一位是1,l的这一位是0,之后小的那个数每一位显然可以任取了,所以后面全部都可以做到一个取1一个取0,于是找到l和r二进制不同的最高位从这位开始全部都是1就是答案。
如果lr的二进制位数不同,首先高位补0补齐,然后看我们能否在r的最高位取1的时候r的最高是不是不一样(如果一样,那么这一位只能取这个值,异或之后就消掉了),一直到第一个不一样的位置,肯定是r的这一位是1,l的这一位是0,之后小的那个数每一位显然可以任取了,所以后面全部都可以做到一个取1一个取0,于是找到l和r二进制不同的最高位从这位开始全部都是1就是答案。
#include<bits/stdc++.h>
#define ll long long
using namespace std;
inline ll read(){
ll s=0,w=1;
char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')w=-1;ch=getchar();}
while(ch>='0'&&ch<='9') s=s*10+ch-'0',ch=getchar();
return s*w;
}
int main(){
long long t;
cin>>t;
while(t--){
long long l,r;
cin>>l>>r;
if(l==r)
cout<<0<<endl;
else{
long long x=1ll<<62;
while((l&x)==(r&x)) {
x>>=1;
}
x<<=1;
cout<<x-1<<endl;
}
}
return 0;
} 位运算得补补了。掌握的不好
京公网安备 11010502036488号