题目描述
基准时间限制:1 秒 空间限制:131072 KB 分值: 10 难度:2级算法题 收藏 关注
M * N的方格,一个机器人从左上走到右下,只能向右或向下走。有多少种不同的走法?由于方法数量可能很大,只需要输出Mod 10^9 + 7的结果。
Input
第1行,2个数M,N,中间用空格隔开。(2 <= m,n <= 1000000)
Output
输出走法的数量 Mod 10^9 + 7。
Input示例
2 3
Output示例
3
解题思想
/**
本题的主要思想还是求乘法逆元。
用的方法是欧拉定理(费马小定理)+快速幂 = 逆元
欧拉定理:如果俩个数a,b互质,则a^φ(b) ≡ 1(mod) b
如果b也是质数,则φ(b)=b-1;
又因为本题是求C(m+n-2,n-1) = (m+n-2)! / ((n-1)!*(m-1)!)
设a=(m+n-2)!
b = (n-1)!*(m-1)!
p = 1e9+7
result = a/b % p
因为a,b是求阶乘,求的过程肯定要%p,
所以原式=(a%p) / (b%p) % p
但是这样求是不对的. 因为 (a%p) / (b%p) %p 不等于 (a/b) % p
但是(a*b) % p = (a%p) * (b%p) %p
所以需要求逆元,将除法转换成乘法
上面是为什么要用逆元,下面是为什么可以用欧拉定理+快速幂求逆元.
解:根据欧拉定理:如果俩个数a,b互质,则a^φ(b) ≡ 1(mod) b
因为result = a/b % p
因为p是质数,所以p和b互质(质数和其他数都互质),
所以b^φ(p) % p =1
又如果b也是质数,则φ(b)=b-1;
所以原式等于b^(p-1) % p =1
也等于b * b^(p-2) % p =1
result = a /b *(1) % p = a/b *(b * b^(p-2)) % p = a * b^(p-2) %p
所以最终结果就变成了求b的(p-2)次幂,用快速幂求就好。
全部解题思路完毕。
*/
代码
import java.util.Scanner;
public class Main{
static final int p = 1000000007;
static final int max = 1000005;
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
int M = sc.nextInt();
int N = sc.nextInt();
//init
long[] fc = new long[max*2];
//阶乘打表
fc[0] = 1;
fc[1] = 1;
for(int i=2; i<max*2; ++i)
fc[i] = (fc[i-1]*i)%p;
//求b^(M-2)
long ans = (quick_pow(fc[N-1],p-2) * quick_pow(fc[M-1], p-2)) % p;
System.out.println((fc[M+N-2]*ans) % p);
}
//快速幂模板
public static long quick_pow(long b, long n){
long ans = 1;
while(n > 0){
if((n&1) == 1)
ans = ans*b%p;
n >>= 1;
b = b*b%p;
}
return (ans+p)%p;
}
}