专栏文章

题解:CF2039C2 Shohag Loves XOR (Hard Version)

CF2039C2题解参与者 2已保存评论 1

文章操作

快速查看文章及其快照的属性,并进行相关操作。

当前评论
1 条
当前快照
1 份
快照标识符
@miqyure0
此快照首次捕获于
2025/12/04 12:59
3 个月前
此快照最后确认于
2025/12/04 12:59
3 个月前
查看原文
仅以此题纪念我赛时会但是写挂了一万年的 C2。

题意翻译

tt 组数据。
y[1,m]y\in \left[1,m\right] 中满足 xyxx\bigoplus y \mid xxyyx\bigoplus y \mid yyy 的数量。

sol

分类讨论两种情况。
xyxx\bigoplus y \mid x 时,令 xy=i×xx\bigoplus y= i\times xy=(i×x)xy=(i\times x)\bigoplus x,得 y[(i1)×x,(i+1)×x]y\in \left[(i-1)\times x,(i+1)\times x\right]
j=mxj=\left\lfloor\dfrac{m}{x}\right\rfloor,得 j×xm<(j+1)×xj\times x\le m<(j+1)\times x
因此当 i+1ji+1\le j 时,yy 一定满足 ymy\le m,由异或运算后非负的性质可得 y1y\ge 1y=0y=0,我们需要排除后者 y=0y=0,即 i=1i=1 时,因此我们把 i[0,j1],i1i\in[0,j-1],i\neq1ii 的数量统计起来。
i=ji=ji=j+1i=j+1 时由值域得可能满足答案,需要特判。
xyyx\bigoplus y \mid y 时,若 y<xy<x,我们可以用枚举的方式统计。
yxy\ge x 时,令 xy=i×y[yx,x+y]x\bigoplus y=i\times y\in\left[y-x,x+y\right]x+y2×yx+y\le2\times y 当且仅当 y=xy=x 时等号成立。
i=0i=0,得 x=yx=y
i=1i=1,得 x=0x=0,舍去。
i=2i=2,得 2×yx+y2\times y\le x+y,所以 y=xy=x,不符合题意,舍去。
至此我们已处理完所有情况,但是我们可能有重复的情况,我们需要去重。
前者中 i[0,j+1],i1i\in[0,j+1],i\neq 1i=0i=0y=xy=x。 其他情况下由 y[(i1)×x,(i+1)×x]y\in \left[(i-1)\times x,(i+1)\times x\right]yxy\ge x,但 y=xy=xi=0i=0y>xy>x
后者由前面的讨论得 yxy\le x,两者的交为 y=xy=x,不要重复统计此情况即可。
空间复杂度为 O(1)O(1)
时间复杂度的开销主要在枚举,复杂度为 O(x)O(\sum x)
代码如下。
CPP
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
int x;
ll m,ans;
template<typename T>
T read(){
	T f=1,x=0;
	char ch=getchar();
	while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
	while(ch>='0'&&ch<='9'){x=x*10+(ch^48);ch=getchar();}
	return f*x;
}
namespace sol{
	void solve(){
		ans=0;
		x=read<int>();m=read<ll>();
		ll j=m/x;
		ans+=j;
		if(1<=((j*x)^x)&&((j*x)^x)<=m)++ans;
		if(1<=(((j+1)*x)^x)&&(((j+1)*x)^x)<=m)++ans;
		if(j-1>=1)--ans;//排除y=0的情况 
		for(int y=1;y<=min((ll)(x-1),m);++y){
			if((x^y)%y==0){
				++ans;
			}
		}
		printf("%lld\n",ans);
	}
}
int main(){
	int T=read<int>();
	while(T--)sol::solve();
	return 0;
}

评论

1 条评论,欢迎与作者交流。

正在加载评论...