51nod-1013 3的幂的和(乘法逆元)

44 篇文章 0 订阅

基准时间限制:1 秒 空间限制:131072 KB 分值: 20  难度:3级算法题
 收藏
 关注
求:3^0 + 3^1 +...+ 3^(N) mod 1000000007
Input
输入一个数N(0 <= N <= 10^9)
Output
输出:计算结果
Input示例
3
Output示例
40

思路:列举前几个可以看出 ans= (f(n)+(f(n)-1)/2 )%MOD          --f(n)=3^n

但是 除法对于取余并没有封闭性,因此要把 除法转换掉,就要用到 乘法逆元.

乘法逆元:若数 x 是 a*x%p=1 则x为 a对于p的乘法逆元,记为 a^(-1)

即 a*a^(-1) = 1  (mod p)

乘法逆元的一大应用是模意义下的除法,除法在模意义下并不是封闭的,但我们可以根据上述公式,将其转化为乘法

x/y=x/y*(y*y^(-1))=x*y^(-1)   (mod p)

利用费马小定理  a^(p-1)=1   (mod p) p 为素数。

则 a^(p-1)=1   (mod p)  -->  a*a^(p-2)=1   (mod p)

由乘法逆元的定义a^(p-2) 即为 a 的乘法逆元。

使用快速幂计算 a^(p-2),时间复杂度为 O(loga)

Code:

#include<iostream>
using namespace std;
typedef long long LL; 

const LL MOD=1000000007;
int n;

int pow(int n,LL p){
    LL ans=1,num=n;
    while(p){
    	if(p&1)	ans=ans*num%MOD;
    	num=num*num%MOD;
		p>>=1;
	}
    return ans;
}
int main()
{
	ios::sync_with_stdio(false);
	while(cin>>n){
		LL a=3,ans=1;
		while(n>0){
			if(n&1)	ans=ans*a%MOD;
			a=a*a%MOD;
			n>>=1;
		}
		LL bi=pow(2,MOD-2);
		ans=(3*ans+2*MOD-1)*bi%MOD;
		cout<<ans<<endl;
	}
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值