roblem A. Huge Numbers
Small input 9 points |
|
Large input 14 points |
|
Problem
Professor Shekhu has another problem for Akki today. He has given him three positive integers A, N and P and wants him to calculate the remainder when AN! is divided by P. As usual, N! denotes the product of the first N positive integers.
Input
The first line of the input gives the number of test cases, T. T lines follow. Each line contains three integers A, N and P, as described above.
Output
For each test case, output one line containing Case #x: y
, where x
is the test case number (starting from 1) and y
is the answer.
Limits
1 ≤ T ≤ 100.
Small dataset
1 ≤ A ≤ 10.
1 ≤ N ≤ 10.
1 ≤ P ≤ 10.
Large dataset
1 ≤ A ≤ 105.
1 ≤ N ≤ 105.
1 ≤ P ≤ 105.
Sample
In Sample Case #1, the answer is the remainder when 21! = 2 is divided by 2, which is 0.
In Sample Case #2, the answer is the remainder when 33! = 36 = 729 is divided by 2, which is 1.
题意很明确,给出a,n,p 求 a^(N!) %p的结果
思路:看数据量,N是可以枚举求的,开始往欧拉函数想,想不下去了。。。。
后来发现化简一下就可以了
a^(N!)%p = a^(1*2*3*...*N)%p = (...(a^1)^2...)^N%p
每层求幂都带着%p,这样枚举1~N,然后每个求幂用快速幂就可以了。
#include <bits/stdc++.h>
using namespace std;
const int N = 310;
#define PI acos(-1)
typedef long long ll;
#define INF 0x3f3f3f3f
int mod = 1000000007;
ll Pow(ll a, int x, int p)
{
ll ret = 1;
while (x)
{
if (x&1)
ret = (ret*a)%p;
a = (a*a)%p;
x >>= 1;
}
return ret;
}
void run()
{
ll a;
int n, p;
scanf("%lld%d%d", &a, &n, &p);
for (int i = 1; i <= n; i++)
{
a = Pow(a, i, p);//求得的结果作为新的底数
}
printf("%lld\n", a);
}
int main()
{
freopen("in.txt", "r", stdin);
freopen("out.txt", "w", stdout);
int T, cas = 1;
scanf("%d", &T);
while (T--)
{
printf("Case #%d: ", cas++);
run();
}
return 0;
}