计算系数
计算系数
https://ac.nowcoder.com/acm/problem/16596
组合数学+快速幂
方法一:递推+打表
首先我第一眼看到的时候就隐隐约约的感觉到了一丝熟悉的味道,这不就是高中数学的组合思想嘛,然后就快速的敲了一遍,但是却忘记了组合数学的规律,组合数学和杨辉三角紧密的联系在一起!!
他的每一项系数正好是杨慧三角每一行的值,所以我们只要把杨辉三角打印出来,然后就可以快速的求解系数了,并且杨辉三角是对称的,所以最后面求解的时候n,m是不影响的,这也验证了组合数学的思想。
另外对于其他的,只需要一个快速幂就可以解决了
#include <bits/stdc++.h> using namespace std; const int maxn = 1010; const int mod = 10007; typedef long long ll; int dp[maxn][maxn]; ll fastpow(ll a, ll b) { ll res = 1; while (b) { if (b & 1) //如果最后一位是1说明这个地方需要乘 res = res * a % mod; a = a * a % mod; //推算乘积 b >>= 1; //右移去掉一位 } return res; } int main() { int a, b, k, n, m; while (~scanf("%d%d%d%d%d", &a, &b, &k, &n, &m)) { for (int i = 0; i <= k; ++i) dp[i][0] = 1; //初始化 for (int i = 1; i <= k; ++i) for (int j = 1; j <= i; ++j) dp[i][j] = (dp[i - 1][j] + dp[i - 1][j - 1]) % mod; ll ans = dp[k][n] % mod * fastpow(a, n) % mod * fastpow(b, m) % mod; printf("%lld\n", ans); } return 0; }
方法二:递归
#include <bits/stdc++.h> using namespace std; typedef long long ll; #define mod 10007 int dp[1010][1010]; int C(int n, int r) { if (n == r || r == 0) return dp[n][r] = 1; if (dp[n][r]) return dp[n][r]; return dp[n][r] = (C(n - 1, r) + C(n - 1, r - 1)) % mod; } ll fastpow(ll a, ll b) { ll res = 1; while (b) { if (b & 1) //如果最后一位是1说明这个地方需要乘 res = res * a % mod; a = a * a % mod; //推算乘积 b >>= 1; //右移去掉一位 } return res; } int main() { int a, b, k, n, m; scanf("%d%d%d%d%d", &a, &b, &k, &n, &m); ll ans = fastpow(a, n) * fastpow(b, m) % mod * C(k, m) % mod; printf("%lld", ans); return 0; }
牛客课后习题题解 文章被收录于专栏
等待蜕变