HDU 5514 Frogs (2015沈阳F题&&容斥+剪枝)
2015-11-08 12:37
369 查看
分析:a[i]a[i]能到达的点为gcd(a[i],m)gcd(a[i],m)的倍数。预处理出所有gcdgcd,两个不同a[i]a[i]能同时到的点为lcm(gcd(a[i],m),gcd(a[j],m))lcm(gcd(a[i],m),gcd(a[j],m))的倍数,容斥写,当遇到当前值是这个gcd(a[i],m)gcd(a[i],m)的倍数是,那么就不用算这个。
具体复杂度我也不会算。
代码:
具体复杂度我也不会算。
代码:
#include <bits/stdc++.h> #define LL long long #define FOR(i,x,y) for(int i = x;i < y;++ i) #define IFOR(i,x,y) for(int i = x;i > y;-- i) using namespace std; const int maxn = 10010; typedef vector <int> VT; int a[maxn],g[maxn]; int gcd(int a,int b){ return b == 0 ? a : gcd(b,a%b); } int n,m; VT s; void init(){ scanf("%d%d",&n,&m); s.clear(); FOR(i,0,n){ scanf("%d",&a[i]); s.push_back(gcd(a[i],m)); } sort(s.begin(),s.end()); VT :: iterator it = unique(s.begin(),s.end()); s.erase(it,s.end()); n = (int)s.size(); FOR(i,0,n) g[i] = s[i]; } LL ans; void dfs(int wei,int num,int sz){ if(wei == n){ if(sz){ LL last = (m-1)/num; LL tem = (last+1)*last*num/2; if(sz%2) ans += tem; else ans -= tem; } return; } if(num % g[wei] == 0) return; dfs(wei+1,num,sz); LL lcm = (LL)num*g[wei]/(LL)gcd(num,g[wei]); if(lcm < (LL)m) dfs(wei+1,lcm,sz+1); } void work(){ ans = 0; if(g[0] == 1){ ans = (LL)m*(m-1)/2; } else dfs(0,1,0); printf("%I64d\n",ans); } int main() { //freopen("test.in","r",stdin); int T,tCase = 0; scanf("%d",&T); while(T--){ printf("Case #%d: ",++tCase); init(); work(); } return 0; }
相关文章推荐
- Linux_NetworkManager_RHEL7
- Oracle dmp文件导入(还原)到不同的表空间和不同的用户下
- 【DirectX 9.0c入门教程】之一 开发环境搭建:安装vs2008 sp1和DirectX SDK
- lightoj 1319 - Monkey Tradition 【CRT】
- mysql学习笔记(3)
- lightoj 1179 - Josephus Problem 【约瑟夫环】
- 驱动开发(4)内核中的内存分配和错误码
- Android笔记—应用更新
- 百度不死心,再次上线百度商城
- 如何保证http传输安全性
- 推荐一本 关于Netty 5.0 的书
- javase中的集合
- 图形效果、图形合成、人脸识别
- 基础 并查集
- iOS 指纹解锁
- Http协议之获取自定义文件Head信息(1)
- XAMPP(Linux版-x86兼容)官网下载
- [读书]初始社会科学
- Javascript静态变量与实例变量
- BFC浅析