首页 > 代码库 > Codeforces Round #275 (Div. 1)
Codeforces Round #275 (Div. 1)
A
题意:给一个N和一个K,求一个1到N的排列,使得abs(a1-a2),abs(a2-a3)...abs(an-1-an)为k个不同的值。
题解:易知我们最大可以凑出N-1个不同的值只要这样1,N,2,N-1,3,....即可
所以我们还按照这个方式来,到凑出来k-1个数之后,把剩下的数从小到大输出即可,这样第k个值为1。
#include <cstdio>#include <cmath>#include <iostream>#include <cstring>#include <algorithm>using namespace std;int n,k,now,nowl,nowr;int main(){ scanf("%d%d",&n,&k); now=0;nowl=1;nowr=n; if (n==3) { if (k==1) printf("1 2 3"); else printf("1 3 2"); return 0; } for (int i=1;i<=k;++i) { if (!now) { printf("%d ",nowl); nowl++; } else { printf("%d ",nowr); nowr--; } now^=1; } if (now==1) for (int i=nowl;i<=nowr;++i) printf("%d ",i); else for (int i=nowr;i>=nowl;--i) printf("%d ",i); return 0;}
B:
题意:求一个N个数的序列,使得满足M个限制条件,限制条件如下给出:
Li Ri Ki 要求a[li]&a[li+1]&a[li+2]&...&a[ri]=ki
题解:按位来做,对于每一位,我们先开一个数组x[i]来表示数列中第i个数这一位是否为1,我们来检索每一个条件,若ki这一位是1,则给li到ri这一段的每个xi都加1,这个可以通过差分在O(N)得到,这样对于每一位我们得到一个x数组,然后我们再来检索每一个条件,若ki这一位不为1,而x[li]到x[ri]均为1,则此时必为无解的情况,否则更新答案即可。
#include <cstdio>#include <cmath>#include <cstring>#include <iostream>#include <algorithm>using namespace std;struct node{ int l,r,w;}q[100005];int a[100005],t[100005],sum[100005],n,m,flag;int work(int x){ memset(sum,0,sizeof(sum)); memset(t,0,sizeof(t)); for (int i=1;i<=m;++i) { int dq=q[i].w&x; if (dq) {t[q[i].l]++;t[q[i].r+1]--;} } for (int i=1;i<=n;++i) t[i]=t[i-1]+t[i]; for (int i=1;i<=n;++i) if (t[i]>0) t[i]=1;else t[i]=0; for (int i=1;i<=n;++i) sum[i]=sum[i-1]+t[i]; for (int i=1;i<=m;++i) { int dq=q[i].w&x; if (!dq) { if (sum[q[i].r]-sum[q[i].l-1]==q[i].r-q[i].l+1) return 0; } else { if (sum[q[i].r]-sum[q[i].l-1]!=q[i].r-q[i].l+1) return 0; } } for (int i=1;i<=n;++i) if (t[i]>0) a[i]|=x; return 1;}int main(){ scanf("%d %d",&n,&m);