1. 程式人生 > >費馬小定理——HDU 4704

費馬小定理——HDU 4704

題意:

    將N拆分成1~n個數,問有多少種組成方法,

    由隔板原理可知,n個數可以看成有n塊板,n-1個間隔,每一個間隔可以有或者沒有,那麼有2^n-1中分法

    重要的是題目中的n很大,到10^1000000,這讓我們無法用矩陣快速冪計算

    費馬小定理:如果a和p互質,那麼a^(p-1) %p = 1;

    那麼設temp = n%(p-1), 我們只要求2^temp%MOD即可

題目程式碼:

#include<bits/stdc++.h>
using namespace std;
const long long  MAX = 1e9 + 7;
char s[1000010];
long long pow1(long long a, long long b)
{
	long long temp, ans;
	temp = a;
	ans = 1;
//	cout<<1111111<<endl;
	while(b)
	{
	//	cout<<ans<<endl;
		if(b & 1)
		{
			ans *= temp;
			ans %= MAX;
				}
		temp *= temp; 
		temp %= MAX;
		b >>= 1;
	}
//	cout<<ans<<endl;
	return ans;
}
int main()
{
	while(scanf("%s", s) != EOF)
	{
		long long n = 0;
		int len = strlen(s);
		for(int i = 0; i < len; i++)
		{
		//	cout<<i<<" "<<n<<endl;
			n = (n*10 + s[i] - '0')%(MAX-1);
		}
		if(n == 0)
			n = MAX-1;
		//cout<<n<<endl;
		long long ans = pow1(2, n-1);
		cout<<ans<<endl;
	}
	return 0;
}