Star (欧拉函数)

2022-10-29,,

题面

Fernando won a compass for his birthday, and now his favorite hobby is drawing stars: first, he marks N points on a circumference, dividing it into N equal arcs; then, he connects each point to the k-th next point, until returning to the first point.

Depending on the value of k, Fernando may or may not reach all points marked on the circumference; when that happens, the star is called complete. For example, when N = 8, the possible stars are shown in the figure below. Stars (a) and (c) are complete, while stars (b) and (d) are not.

Depending on the value of N, it may be possible to draw many different stars; Fernando asked you to write a program that, given N, determines the number of complete stars he can draw.

Input

The input contains several test cases. Each test case contains a single line, containing a single integer N (3 ≤ N < 2^31), indicating the number of arcs in which the circumference was divided.

Output

For each test case, your program must print a single line containing a single integer, indicating the number of complete stars that can be drawn.

题解

考虑这个圆上的一个点为起点

如果选择一个距离 K 使之可以被遍历完,那么一定有一个时候,它可以跳到与A相邻的B点,这是肯定的吧

反过来说,如果对于某个K,跳的次数为X,如果 XK mod N = 1,那么K一定是一种合法方案,

这是不是就意味着,X是K关于N的逆元?

我们知道,K有关于N的逆元的条件是K与N互质,

那么答案就为 φ(N) / 2

为什么要除以二呢,因为 K = p 和 K = N - p画出来的图长得一样,

CODE

(笔者vjudge暂时被封)

(以下是Alzh的代码)

#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std; typedef long long LL; LL Euler(LL n)
{
LL res=n;
for(LL i=2; i*i<=n; ++i)
{
if(n%i==0)
{
res=res/i*(i-1);
while(n%i==0)
n/=i;
}
}
if(n>1)
res=res/n*(n-1);
return res;
} int main()
{
LL n;
while(~scanf("%lld",&n))
printf("%lld\n",Euler(n)/2);
return 0;
}

Star (欧拉函数)的相关教程结束。

《Star (欧拉函数).doc》

下载本文的Word格式文档,以方便收藏与打印。