[300iq]Bitwise Xor
Posted StaroForgin
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[300iq]Bitwise Xor相关的知识,希望对你有一定的参考价值。
Bitwise Xor
题解
首先我们可以发现一个性质,若
x
<
y
<
z
x<y<z
x<y<z,那么一定有
x
⊕
z
⩾
min
(
x
⊕
y
,
y
⊕
z
)
x\\oplus z\\geqslant \\min(x\\oplus y,y\\oplus z)
x⊕z⩾min(x⊕y,y⊕z)。
这个结论可以从二进制的角度分析
x
⊕
y
x\\oplus y
x⊕y与
y
⊕
z
y\\oplus z
y⊕z的异或过程得出。
显然二进制的比较可以从高位到低位依次比较。
如果
x
⊕
y
x\\oplus y
x⊕y与
y
⊕
z
y\\oplus z
y⊕z在这一位上都是
0
0
0,显然,
x
⊕
z
x\\oplus z
x⊕z有这两种异或起来也应该是
0
0
0,这个位置两者没有区别,我们会继续往下比较,这部分也象征着
x
,
y
,
z
x,y,z
x,y,z在这前面几位都是一样的。
若
x
⊕
y
x\\oplus y
x⊕y与
y
⊕
z
y\\oplus z
y⊕z其中有一个
1
1
1,那么
x
⊕
z
x\\oplus z
x⊕z这一位也应该是
1
1
1,比是
0
0
0的那一个大,此时便已经符合我们的条件了。
若
x
⊕
y
x\\oplus y
x⊕y与
y
⊕
z
y\\oplus z
y⊕z两个都是
1
1
1,要么
y
y
y在这一位上为
1
1
1,
x
,
z
x,z
x,z在这一位上为
0
0
0,要么反过来,
x
,
z
x,z
x,z为
1
1
1,
y
y
y为
0
0
0。
但由于
z
>
y
z>y
z>y,所以
z
z
z肯定在前面的某一位比
y
y
y大,故它应该在之前就进入了前一种情况,不会比较到这里,第一种方案被否决。
同理
y
>
x
y>x
y>x,第
2
2
2种方案也被否决。
所以它们一定会在第
2
2
2种情况决出胜负,所以一定有上面的条件成立。
有了上面的性质,我们可以发现,如果我们已经有了一个满足答案的集合
S
S
S,那么
w
w
w只要与
S
S
S中离它最近的两个数异或起来比
x
x
x大,那么它一定与
S
S
S中所有数异或起来都比
x
x
x大。
2
2
2个数显然不好记录,但我们可以从小到大依次加入
a
i
a_i
ai,这样的话每次加入的
a
i
a_i
ai一定是最大的,只需要与集合中最大的一个数比较大小,只要与这个数异或起来大于
x
x
x就行了。
我们记
d
p
i
dp_i
dpi表示最大值为
a
i
a_i
ai的合法集合的个数,我们转移
d
p
j
dp_j
dpj时,只需要找到
a
j
⊕
a
i
⩾
x
a_j\\oplus a_i\\geqslant x
aj⊕ai⩾x的所有
a
i
a_i
ai,加上
d
p
i
dp_i
dpi的和就可以转移了。
显然找到
a
i
⊕
a
j
⩾
x
a_i\\oplus a_j\\geqslant x
ai⊕aj⩾x的
d
p
i
dp_i
dpi和可以使用
T
r
i
e
Trie
Trie树上,每次只会查询一条链,再将新的插入进去即可。
时间复杂度 O ( n log a ) O\\left(n\\log a\\right) O(nloga)。
源码
#include<bits/stdc++.h>
using namespace std;
#define MAXN 300005
#define lowbit(x) (x&-x)
#define reg register
#define pb push_back
#define mkpr make_pair
#define fir first
#define sec second
typedef long long LL;
typedef unsigned long long uLL;
typedef long double ld;
typedef pair<int,int> pii;
const int INF=0x3f3f3f3f;
const int mo=998244353;
const int mod=1e5+3;
const int inv2=5e8+4;
const int jzm=2333;
const int zero=20000;
const int n1=1000;
const int M=100000;
const int orG=3,ivG=332748118;
const long double Pi=acos(-1.0);
const double eps=1e-12;
template<typename _T>
_T Fabs(_T x)return x<0?-x:x;
template<typename _T>
void read(_T &x)
_T f=1;x=0;char s=getchar();
while(s>'9'||s<'0')if(s=='-')f=-1;s=getchar();
while('0'<=s&&s<='9')x=(x<<3)+(x<<1)+(s^48);s=getchar();
x*=f;
template<typename _T>
void print(_T x)if(x<0)x=(~x)+1;putchar('-');if(x>9)print(x/10);putchar(x%10+'0');
int gcd(int a,int b)return !b?a:gcd(b,a%b);
int add(int x,int y,int p)return x+y<p?x+y:x+y-p;
void Add(int &x,int y,int p)x=add(x,y,p);
int qkpow(int a,int s,int p)int t=1;while(s)if(s&1)t=1ll*t*a%p;a=1ll*a*a%p;s>>=1;return t;
int n,root,dp[MAXN],ans;LL X,a[MAXN];
struct mingint sum,ch[2];;
class TrieTree
private:
ming tr[MAXN*70];int tot;
public:
void insert(int &rt,int dp,LL val,int aw)
if(!rt)rt=++tot;Add(tr[rt].sum,aw,mo);if(dp<0)return ;
insert(tr[rt].ch[(val>>dp)&1LL],dp-1,val,aw);
int query(int &rt,int dp,LL val)
if(!rt)return 0;if(dp<0)return tr[rt].sum;
int res=0,typ=(int)((val>>dp)&1LL);
if((X>>dp)&1LL)Add(res,query(tr[rt].ch[typ^1],dp-1,val),mo);
else Add(res,tr[tr[rt].ch[typ^1]].sum,mo),
Add(res,query(tr[rt].ch[typ],dp-1,val),mo);
return res;
T;
signed main()
read(n);read(X);
for(int i=1;i<=n;i++)read(a[i]);
sort(a+1,a+n+1);
for(int i带有 ufunc bitwise_xor 的 TypeError
codeforces gym 102268 300iq round
CF778B(round 402 div.2 E) Bitwise Formula
「题解」300iq Contest 2 H. Honorable Mention