[POJ3372]Candy Distribution
Posted StaroForgin
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[POJ3372]Candy Distribution相关的知识,希望对你有一定的参考价值。
Candy Distribution
题解
相当有趣的题。
首先,我们可以发现一点,当我们给了
n
n
n个小朋友糖时,我们总共走了
n
(
n
−
1
)
2
\\fracn(n-1)2
2n(n−1)步。
如果
n
n
n是奇数,我们肯定现在已经回到了
1
1
1号位,我们只需要说明我们在这
n
n
n步中给了每个小朋友恰好一颗糖即可。
如果我们的
n
n
n是偶数,那我们现在肯定是在位置
n
2
\\fracn2
2n,也就是说后面
n
n
n步于先前
n
2
\\fracn2
2n步相对于我们
n
2
\\fracn2
2n的线得到的应该是等价的。
也就是说,我们真正走到每个点的次数,在这种情况下,前
n
2
\\fracn2
2n块每个点被走到的次数是与后
n
2
\\fracn2
2n块的等价点被走到的次数相同,可以将后
n
2
\\fracn2
2n步反过来考虑,显然它反过来走是与前
n
2
\\fracn2
2n步正着走等价的。
所以,我们可以将它规约到
n
2
\\fracn2
2n的子问题上去考虑,因为只要在
n
2
\\fracn2
2n的子问题能够合法,那我们
n
n
n的问题也是一定合法的,反之亦然。
如果我们
n
2
\\fracn2
2n的问题是奇数,那么也有我们上面能够覆盖满的条件,否则我们可以继续规约到
n
4
\\fracn4
4n的子问题上。
所以我们只需要看哪些奇数能够有解。
我们记
f
(
i
)
=
i
(
i
−
1
)
2
f(i)=\\fraci(i-1)2
f(i)=2i(i−1),那么我们只需要
f
(
1
)
,
f
(
2
)
,
.
.
.
f
(
n
)
f(1),f(2),...f(n)
f(1),f(2),...f(n)能够覆盖满
n
n
n的简化剩余系。
也就是说,
∀
i
,
j
∈
[
1
,
n
]
(
i
≠
j
)
,
f
(
i
)
≠
f
(
j
)
\\forall i,j\\in[1,n](i\\not =j),f(i)\\not =f(j)
∀i,j∈[1,n](i=j),f(i)=f(j)。
可以得到
(
i
−
j
)
(
i
+
j
−
1
)
2
≢
0
(
m
o
d
n
)
\\frac(i-j)(i+j-1)2\\not \\equiv 0(\\mod n)
2(i−j)(i+j−1)≡0(modn)。
显然,
(
i
−
j
)
(i-j)
(i−j)与
(
i
+
j
−
1
)
(i+j-1)
(i+j−1)的奇偶性不同,所以我们的
(
i
−
j
)
(
i
+
j
−
1
)
2
\\frac(i-j)(i+j-1)2
2(i−j)(i+j−1)必定有一个奇数因子。
如果这个奇数因子是由
i
+
j
−
1
i+j-1
i+j−1构成的,当
n
>
1
n>1
n>1,我们显然可以找到找到这样的一对
(
i
,
j
)
(i,j)
(i,j),使得
i
+
j
−
1
=
n
i+j-1=n
i+j−1=n,从而使得无解。
也就是说,如果我们的
n
n
n含有除
2
2
2以外的质因子,也就是说它不是
2
2
2的幂,它就无解,否则一定有解。
时间复杂度 O ( log n ) O\\left(\\log\\,n\\right) O(logn)。
源码
这也需要代码吗?
#include<cstdio>
#include<cmath>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define lowbit(x) (x&-x)
#define reg register
#define pb push_back
#define mkpr make_pair
#define fir first
#define sec second
typedef long long LL;
typedef unsigned long long uLL;
typedef long double ld;
const double INF=1e18;
const int mo=998244353;
const int inv2=499122177;
const double jzm=0.997;
const int zero=100;
const int lim=200;
const int orG=3,invG=332748118;
const double Pi=acos(-1.0);
const double eps=1e-5;
typedef pair<double,int> pii;
template<typename _T>
_T Fabs(_T x)return x<0?-x:x;
template<typename _T>
void read(_T &x)
_T f=1;x=0;char s=getchar();
while(s>'9'||s<'0')if(s=='-')f=-1;s=getchar();
while('0'<=s&&s<='9')x=(x<<3)+(x<<1)+(s^48);s=getchar();
x*=f;
template<typename _T>
void print(_T x)if(x<0)x=(~x)+1;putchar('-');if(x>9)print(x/10);putchar(x%10+'0');
int gcd(int a,int b)return !b?a:gcd(b,a%b);
int add(int x,int y,int p)return x+y<p?x+y:x+y-p;
void Add(int &x,int y,int p)x=add(x,y,p);
int n;
signed main()
while(scanf("%d",&n)!=EOF)
while(!(n&1))n>>=1;
puts(n==1?"YES":"NO");
return 0;
谢谢!!!
以上是关于[POJ3372]Candy Distribution的主要内容,如果未能解决你的问题,请参考以下文章
Poj 3083 Children of the Candy Corn
POJ 3083Children of the Candy Corn