【BZOJ1008】【HNOI2008】越狱(数学排列组合题)
1008: [HNOI2008]越狱
Time Limit: 1 Sec Memory Limit: 162 MBSubmit: 3140 Solved: 1317
[Submit][Status]
Description
监狱有连续编号为1...N的N个房间,每个房间关押一个犯人,有M种宗教,每个犯人可能信仰其中一种。如果相邻房间的犯人的宗教相同,就可能发生越狱,求有多少种状态可能发生越狱
Input
输入两个整数M,N.1<=M<=10^8,1<=N<=10^12
Output
可能越狱的状态数,模100003取余
Sample Input
2 3
Sample Output
6
HINT
6种状态为(000)(001)(011)(100)(110)(111)
Source
分析:高中数学题……可能越狱=总-不可能越狱
一共n个位置,每个位置m个可能,所以总=m^n
第一个位置有m个可能;第二个位置要和第一个位置不同,故m-1个可能;第三个位置要和第二个位置不同,故m-1个可能……;不可能越狱=m*(m-1)^(n-1)
综上所述,ans=m^n-m*(m-1)^(n-1),然后算的时候每个地方mod一下就行了。注意到n很大,所以快速幂搞一下……
(这恐怕是bzoj最水的一题了,不过那些拼空间的大牛真是丧心病狂!16kB怎么办到的!)
1 #include<algorithm> 2 #include<cstring> 3 #include<cstdio> 4 using namespace std; 5 const int p=100003; 6 long long power(long long a,long long b) 7 { 8 long long ans=1; 9 while(b>0) 10 { 11 if(b%2==1) ans=(ans*a)%p; 12 a=(a*a)%p; 13 b/=2; 14 } 15 return ans; 16 } 17 int main() 18 { 19 long long n,m; 20 scanf("%lld%lld",&m,&n); 21 long long ans=(power(m,n)-(m*power(m-1,n-1))%p)%p; 22 if(ans<0) ans+=p; 23 printf("%lld",ans); 24 return 0; 25 }