首页 > 代码库 > poj 1284 Primitive Roots 【原根】【数论】
poj 1284 Primitive Roots 【原根】【数论】
题目链接 : 传送门
题目大意: 求一个质数的原根个数。
先普及一下原根的定义:
设m是正整数,a是整数,若a模m的阶等于euler(m),则称a为模m的一个原根。
eg: m=7,euler(7) = 6(1,2,3,4,5,6)
则:
- 1 1^(n)mod7=1! = 6
- 2 2^(n)mod7={2 4 1}!=6
- 3 3^(n)mod7={3,2,6,4,5,1}==6 故3是模7的原根
- 4 4^(n)mod7={4,2,1}!=6
- 5 5^(n)mod7={5,4,6,2,3,1}==6 故5是模7的原根
- 6 6^(n)mod7={6,1}!=6
故7的原根有两个。
判断方法:判断g^(m-1) = 1 (mod m)是否当且当指数为m-1的时候成立
模m有原根的充要条件是m= 1,2,4,p,2p,p^n,其中p是奇质数,n是任意正整数。
有一个规律,任何一个质数的原根个数都是等于euler(n-1)的值。
则本题的代码如下:
#include<iostream> #include<stdio.h> using namespace std; //直接求解欧拉函数,返回euler(n) int euler(int n){ int res=n,a=n; for(int i=2;i*i<=a;i++) { if(a%i==0) { res=res/i*(i-1); //先进行除法是为了防止中间数据的溢出 while(a%i==0) a/=i; } } if(a>1) res=res/a*(a-1); return res; } int main () { int num; while(~scanf("%d",&num)) { printf("%d\n",euler(num-1)); } }
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。