UVA
来源:互联网 发布:合肥培训软件 编辑:程序博客网 时间:2024/06/17 18:01
题目链接:https://vjudge.net/problem/UVA-12716
题目大意:求出1<=b<=a<=n的二元组(a,b),使得gcd(a,b)=a^b
解题思路:因为有^,所以应该先想到^对应的性质,即a^b^a=b,所以a^gcd(a,b)=a^a^b=b,由于gcd(a,b)必定是a的因子,所以只用枚举a的因子,求出相应的b之后检验gcd(a,b)是否与之前的相同。接着进行优化,首先要知道几个结论,假设a>b,1.a-b>=gcd(a,b)
证明:
因为a=t1*gcd(a,b),b=t2*gcd(a,b),所以a-b=(t1-t2)*gcd(a,b)>=gcd(a,b)
2.a-b<=a^b
证明:把a和b都先转化成二进制,然后把a中的0与b中的1互换,得到a1,b1,并且a1>=a,b1<=b,并且可以发现a1-b1=a1^b1(这个我不会证明),所以a1^b1=a^b>=a-b
综上,a-b=a^b=gcd(a,b)
所以在枚举因子时不需要调用函数求gcd(a,b),直接相减即为gcd(a,b)
但是,做到这里还是会超时,要进行预处理,对于每个二元组中的a,都可以记录a所具有的b的个数,然后一直向上累加,就可以得到小于等于n的总个数,然后直接输出即可
AC代码:
#include<cstdio>#include<iostream>using namespace std;typedef long long LL;const int MAXN = 30000000 + 5;int ans[MAXN];int main(){ for (int i = 1;i < MAXN;i++) { for (int j = i;j < MAXN;j += i) { int b = i^j; if (b <= j&&b >= 1 && j - b == i) ans[j]++; } } for (int i = 2;i < MAXN;i++) ans[i] += ans[i - 1]; int t;scanf("%d", &t); for(int p=1;p<=t;p++) { int n;scanf("%d", &n); printf("Case %d: %d\n", p, ans[n]); } return 0;}
阅读全文
0 0
- uva
- UVA
- UVA
- UVA
- uva
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- UVA
- 犀牛Rhino教程合集37部
- 4比较三个数的大小输出最大的值并从小到大排序输出
- NOIP模拟赛八连测摸鱼划水睡觉搞机记
- 走出迷宫
- Hibernate中表与表的多对多关系
- UVA
- Android 单独抽取 WebRtc-NS/NSX(音频降噪) 模块
- c++深拷贝浅拷贝
- 简单菱形
- RSA加密算法、数字签名和数字证书及其java实现
- python——linalg说明
- 计算机视觉·常用数据集·图像分割
- Add All(贪心,vector)
- 常见深度学习模型参数总结