OR(牛客第八场)
Posted Jozky86
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了OR(牛客第八场)相关的知识,希望对你有一定的参考价值。
题意:
给你一个数组b和c(数值位于下标2到n)
问是否存在一个a序列,
b
i
=
a
i
−
1
o
r
a
i
bi=a_{i-1} or a_{i}
bi=ai−1orai ,
c
i
=
a
i
−
1
+
a
i
c_{i}=a_{i-1}+a_{i}
ci=ai−1+ai
题解:
我是这样想的,对于每一个bi和ci(i从2开始),都可以确定ai的取值情况,然后我们再计算bi+1和ci+1时,可以根据上一轮ai得到的情况来确定本轮ai+1的情况。
如何通过bi和ci确定ai的取值呢?
我们利用二进制来判断,对于bi和ci的每一位分析,从第0位到第31位依次分析,
- 考虑第j位时,f表示当前是否有进位
- 如果b=0,c=0,f=0,那么ai,ai-1的第j位为0
- 如果b=1,c=1,f=1,那么ai,ai-1为1
- 如果b=1,c=1,f=1,那么ai和ai-1一个为0,一个为1
- 如果b=1,c=0,f=1,那么ai和ai-1一个为0
- 如果b=1,c=0,f=0,那么ai,ai-1为1,且会产生进位f=1
- 如果b=0,c=1,f=1,那么ai,ai-1为0,进位在此处用掉,进位消失,f=0
- 不满足上列情况,a无法取到值
F[i]表示第i个位置的情况
F[i]=2表示第i个位置有两个值可以取,如果ai取1,则ai-1取0,反之(初始化为-1)
F[i]=1/0:分别表示当前位置取1或0
F[i]=-1:说明当前位置无法取到值
F[i]会不断更新,F[i]的作用相当于将Ai的取值情况与Ai-1相连(Ai-1的情况就是通过F[i]来表示),完事后并更新F[i],给后面Ai+1接着使用
w表示当前第j位的取值情况
- 如果w=-1,则F[i]=-1
- 如果w=0/1&&F[j]==2,则F[j]=w
- 如果w=2&&F[j]!=2,则F[j]=F[j] ^ 1(ai-1这一个位置取w(0或1),而ai与ai-1是两种取值,ai的取值是w ^ 1)
- 如果w=0&&F[j]=1,则F[j]=-1;
- 如果w=1&&F[j]=0,则F[j]=-1;
然后更新答案
详细看代码
代码:
#include<bits/stdc++.h>
#define debug(a,b) printf("%s = %d\\n",a,b);
using namespace std;
typedef long long ll;
typedef pair<int, int> PII;
clock_t startTime, endTime;
//Fe~Jozky
const ll INF_ll=1e18;
const int INF_int=0x3f3f3f3f;
inline ll read(){
ll s=0,w=1ll;
char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')w=-1ll;ch=getchar();}
while(ch>='0'&&ch<='9') s=s*10ll+((ch-'0')*1ll),ch=getchar();//s=(s<<3)+(s<<1)+(ch^48);
return s*w;
}
void rd_test(){
#ifdef ONLINE_JUDGE
#else
startTime = clock(); //计时开始
freopen("in.txt","r",stdin);
#endif
}
void Time_test(){
#ifdef ONLINE_JUDGE
#else
endTime = clock(); //计时结束
printf("\\n运行时间为:%lfs\\n",(double)(endTime - startTime) / CLOCKS_PER_SEC);
#endif
}
const int maxn=2e5+9;
ll b[maxn],c[maxn],F[maxn];
int main()
{
//rd_test();
int n;
cin>>n;
ll sum=1e11;
for(int i=2;i<=n;i++){
cin>>b[i];
}
for(int i=2;i<=n;i++){
cin>>c[i];
}
for(int i=0;i<=33;i++)F[i]=2;
for(int i=2;i<=n;i++){
ll tot=1;
ll w=0;
int f=0;
for(int j=0;j<=31;j++){
int x=((b[i]>>j)&1);
int y=((c[i]>>j)&1);
if(x==0&&y==0&&f==0)w=0;
else if(x==1&&y==1){
if(f==1)
{
w=1;
}
else w=2;
}
else if(x==1&&y==0){
if(f==1)
{
w=2;
f=1;
}
else{
w=1;
f=1;
}
}
else if(x==0&&y==1&&f==1){
f=0;
w=0;
}
else {
w=-1;
}
if(w==-1)F[j]=-1;
else if(F[j]==2&&w!=2) F[j]=w;
else if(w==2&&F[j]!=2)F[j]=F[j]^1;
else if(F[j]==1&&w==0)F[j]=-1;
else if(F[j]==0&&w==1) F[j]=-1;
if(F[j]==1)tot=1ll*tot*1;
else if(F[j]==0)tot=1ll*tot*1;
else if(F[j]==2)tot=1ll*tot*2;
else if(F[j]==-1)tot=1ll*tot*0;
}
if(f==1)tot=0;
sum=min(sum,tot);
}
cout<<sum;
//Time_test();
}
以上是关于OR(牛客第八场)的主要内容,如果未能解决你的问题,请参考以下文章