题目链接

题意:有n只青蛙,m个石头(围成圆圈)。第i只青蛙每次只能条ai个石头,问最后所有青蛙跳过的石头的下标总和是多少?

题解:暴力肯定会超时,首先分解出m的因子,自己本身不用分,因为石头编号是0到m-1,第i只青蛙只能走到gcd(ai, m)的位置,我们就可以把m的因子提取出来,然后对青蛙能走到的因子位置打标记。两个数组,第一个数组a代表是否能走到该因子,第二个数组b表示是否已经加过了,加过了几次,遍历到那个因子的时候要加上(a[i]-b[i])倍的数,这个数很可能是负数。至于公式利用等差数列前n项和可以得出。

注意这道题是因子分解而不是素因子分解,因为对于12来说2和4是不一样的。

注意这道题不是对数进行操作而是对因子进行操作。

#include <iostream>
#include <cstdio>
#include <cmath>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
ll gcd(ll a,ll b)
{
return b==?a:gcd(b,a%b);
}
const int maxn=1e5+;
ll cnt=,prime[maxn];
void solve(ll m)
{
cnt=;//注意初始化
prime[cnt++]=;
for(int i=; i<sqrt(m); i++)
{
if(m%i==)
{
prime[cnt++]=i;
prime[cnt++]=m/i;
}
}
ll tmp=sqrt(m);
if(tmp*tmp==m)
prime[cnt++]=tmp;
sort(prime,prime+cnt);
}
int main()
{
int t,cas=;
scanf("%d",&t);
while(t--)
{
ll n,m,data,tmp;
scanf("%lld%lld",&n,&m);
memset(prime,,sizeof(prime));
solve(m);
ll a[maxn],b[maxn];
memset(a,,sizeof(a));//标记
memset(b,,sizeof(b));//算过了几次
for(int i=; i<n; i++)
{
scanf("%lld",&data);
tmp=gcd(data,m);
for(int j=; j<cnt; j++)
{
if(prime[j]%tmp==)
a[j]=;
}
}
ll ans=;
for(int i=; i<cnt; i++)
{
ll num=a[i]-b[i];
if(num!=)
{
ll tmp=(m-)/prime[i];
ans=ans+tmp*(tmp+)/*prime[i]*num;
for(int j=i; j<cnt; j++)
{
if(prime[j]%prime[i]==)
b[j]=b[j]+num; //注意是b表示数目
}
}
}
printf("Case #%d: %lld\n",cas++,ans);
}
return ;
}

更新版:

#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
using namespace std;
typedef long long ll;
ll gcd(ll a,ll b)
{
return b==?a:gcd(b,a%b);
}
const int maxn=1e5+;
ll prime[maxn],a[maxn];
int cnt=;
void solve(ll m)
{
memset(a,,sizeof(a));
memset(prime,,sizeof(prime));
cnt=;
prime[cnt++]=;
for(int i=;i<sqrt(m);i++)
{
if(m%i==)
{
prime[cnt++]=i;
prime[cnt++]=m/i;
}
}
if(ll(sqrt(m))*ll(sqrt(m))==m) prime[cnt++]=ll(sqrt(m));
sort(prime,prime+cnt);
}
int main()
{
int t,cas=;
scanf("%d",&t);
while(t--)
{
ll n,m,data;
scanf("%lld%lld",&n,&m);
solve(m);
for(int i=;i<n;i++)
{
scanf("%lld",&data);
data=gcd(data,m);
for(int j=;j<cnt;j++)
if(prime[j]%data==) a[j]=;
}
ll ans=;
for(int i=;i<cnt;i++)
{
ll num=a[i];
if(num!=)
{
ll tmp=(m-)/prime[i];
ans+=tmp*(tmp+)/*prime[i]*num;
for(int j=i+;j<cnt;j++)
if(prime[j]%prime[i]==) a[j]-=num;
}
}
printf("Case #%d: %lld\n",cas++,ans);
}
return ;
}

HDU 5514 Frogs (容斥原理+因子分解)的更多相关文章

  1. HDU 5514 Frogs (容斥原理)

    题目链接 : http://acm.hdu.edu.cn/showproblem.php?pid=5514 题意 : 有m个石子围成一圈, 有n只青蛙从跳石子, 都从0号石子开始, 每只能越过a[i] ...

  2. hdu 5514 Frogs(容斥)

    Frogs Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submi ...

  3. HDU 5514 Frogs(容斥原理)

    [题目链接] http://acm.hdu.edu.cn/showproblem.php?pid=5514 [题目大意] m个石子围成一圈,标号为0~m-1,现在有n只青蛙,每只每次跳a[i]个石子, ...

  4. HDU 5514 Frogs 容斥定理

    Frogs Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://acm.hdu.edu.cn/showproblem.php?pid=5514 De ...

  5. HDU 5514 Frogs

    Frogs Time Limit: 1000ms Memory Limit: 65536KB This problem will be judged on HDU. Original ID: 5514 ...

  6. HDU 5514 Frogs 欧拉函数

    题意: 有\(m(1 \leq m \leq 10^9)\)个石子排成一圈,编号分别为\(0,1,2 \cdots m-1\). 现在在\(0\)号石头上有\(n(1 \leq n \leq 10^4 ...

  7. HDU 5514 Frogs (数论容斥)

    题意:有n只青蛙,m个石头(围成圆圈).第i只青蛙每次只能条ai个石头,问最后所有青蛙跳过的石头的下标总和是多少? 析:首先可以知道的是第 i 只青蛙可以跳到 k * gcd(ai, m),然后我就计 ...

  8. hdu 5514 Frogs 容斥思想+gcd 银牌题

    Frogs Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submi ...

  9. HDU 5514.Frogs-欧拉函数 or 容斥原理

    Frogs Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submi ...

随机推荐

  1. 求第N数大问题

    问题: InputThe first line of input contains a single integer P, (1 ≤ P ≤ 1000), which is the number of ...

  2. 一个项目中哪些文件是要上传到 git上的,哪些是不必要的

  3. 【poj3070】 Fibonacci

    http://poj.org/problem?id=3070 (题目链接) 题意 用矩阵乘法求fibonacci数列的第n项. Solution 矩乘入门题啊,题目把题解已经说的很清楚里= =. 矩乘 ...

  4. HDU1698 Just a Hook

    Description In the game of DotA, Pudge’s meat hook is actually the most horrible thing for most of t ...

  5. vim YouCompleteMe

    http://www.ithao123.cn/content-1906969.html http://www.it165.net/os/html/201503/12190.html

  6. codeforce626D (概率)

    D. Jerry's Protest time limit per test 2 seconds memory limit per test 256 megabytes input standard ...

  7. Nutch的配置以及动态网站的抓取

    http://blog.csdn.net/jimanyu/article/details/5619949 一:配置Nutch: 1.解压缩的nutch后,以抓取http://www.163.com/为 ...

  8. Linux之入侵痕迹清理总结

    rm -f -r /var/log/*rm .bash_historyrm recently_used

  9. JS 省,市,区

    // 纯JS省市区三级联动 // 2011-11-30 by http://www.cnblogs.com/zjfree var addressInit = function (_cmbProvinc ...

  10. 通过开源程序同时解决DNS劫持和DNS污染的问题

    我们知道,某些网络运营商为了某些目的,对DNS进行了某些操作,导致使用ISP的正常上网设置无法通过域名取得正确的IP地址.常用的手段有:DNS劫持和DNS污染.关于DNS劫持和DNS污染的区别,请查找 ...