原根小结 (poj 1284)

关于原根的一些知识点:

设m是正整数,a是整数,若a模m的阶等于φ(m),则称a为模m的一个原根。(其中φ(m)表示m的欧拉函数

定义1:,使得成立的最小的,称为对模的阶,记为


定理1:如果模有原根,那么它一共有个原根。


定理2:,则


定理3:如果为素数,那么素数一定存在原根,并且模的原根的个数为


定理4:是正整数,是整数,若的阶等于,则称为模的一个原根。


   假设一个数对于模来说是原根,那么的结果两两不同,且有,那么可以称为是模的一个原根,归根到底就是当且仅当指数为的时候成立。(这里是素数)


定理5:模有原根的充要条件:,其中是奇素数。

 


求模素数原根的方法:素因子分解,即的标准分解式,若恒有


          


成立,就是的原根。(对于合数求原根,只需把换成即可)

以上内容转自http://blog.csdn.net/acdreamers/article/details/8883285


我的补充:

1.如果g为p的原根,则:g^i mod p ≠ g^j mod p (p为素数), 其中i ≠ j且i, j介於1至(p-1)之间


求原根的代码:

/*求原根模板
 */
#include
   
   
    
    
#include
    
    
     
     
#include
     
     
      
      
using namespace std;
#define LL __int64
vector
      
      
       
        a;
LL Ext_gcd(LL a,LL b,LL &x,LL &y){
    if(b==0) { x=1, y=0; return a; }
    LL ret= Ext_gcd(b,a%b,y,x);
    y-= a/b*x;
    return ret;
}

LL Inv(LL a,int m){   //求逆元
    LL d,x,y,t= (LL)m;
    d= Ext_gcd(a,t,x,y);
    if(d==1) return (x%t+t)%t;
    return -1;
}

LL a_b_MOD_c(LL a,LL b,LL mod){
	LL ret = 1;
	a %= mod;
	while(b){
		if(b & 1) ret = ret * a % mod;
		a = a * a % mod;
		b >>= 1;
	}
	return ret;
}
bool g_test(LL g,LL p){
	for(LL i=0;i
       
       
      
      
     
     
    
    
   
   


题目:

poj 1284
题意:
给出一个数n,求原根数目。
限制:
3 <= n < 65536; n为奇素数。
思路:
因为n是素数,所以模n的原根数=phi(phi(n))=phi(n-1)。
phi(i) 可以预处理出来。


/*poj 1284
  题意:
  给出一个数n,求原根数目。
  限制:
  3 <= n < 65536; n为奇素数。
  思路:
  因为n是素数,所以模n的原根数=phi(phi(n))=phi(n-1)。
  phi(i) 可以预处理出来。
 */
#include
    
    
     
     
#include
     
     
      
      
using namespace std;
const int N=100005;
int pri[N],pcnt;
int phi[N];
void getphi(){
	phi[1]=1;
	for(int i=2;i
      
      
     
     
    
    

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值