题目:起床困难综合症
思路:
由于每个二进制位的位运算互不影响,所以可以把m和t都拆成二进制表示,一位一位的考虑。
代码:
#include<bits/stdc++.h>
using namespace std;
#define maxn 100000
#define read(x) scanf("%d",&x)
int n,m;
int opr[maxn+5],a[maxn+5];
int b[50];
int c[maxn+5][50];
void cuta(int x) {
int y=a[x],len=0;
while(y) {
c[x][++len]=y&1;
y>>=1;
}
for(int i=1;i<=30/2;i++) swap(c[x][i],c[x][30-i+1]);
}
void readin() {
read(n),read(m);
for(int i=1;i<=n;i++) {
string op;
cin>>op;
opr[i]=(op[0]=='A'?1:(op[0]=='O'?2:3));
read(a[i]);
cuta(i);
}
}
void cutm() {
int x=m,len=0;
while(x) {
b[++len]=x&1;
x>>=1;
}
for(int i=1;i<=30/2;i++) swap(b[i],b[30-i+1]);
}
int slv(int j,int y) {
for(int i=1;i<=n;i++) {
if(opr[i]==1) y&=c[i][j];
else if(opr[i]==2) y|=c[i][j];
else y^=c[i][j];
}
return y;
}
int main() {
readin();
cutm();
int ans=0,fl=0;
for(int i=1;i<=30;i++) {
int x=slv(i,0);
if(b[i]==1||fl) {
ans<<=1;
if(slv(i,1)==1&&!x) ans++;
else {
ans+=x;
fl=true;
}
} else ans<<=1,ans+=x;
}
printf("%d",ans);
return 0;
}