标签:题意 bsp sum force 空间 题目 初始化 解法 const
这道题主要就是求n组东东的放置方法,约束条件是在任意第i组放完之前,i-1组必须放完,问有多少放置方法
组合数学+简单的DP,解法思路就是在任意放置i组时,除了最后一位一定是i,剩下任意插空放置
int ksm(int a,int b,int p) { int res=1; while(b) { if(b&1) res=1ll*res*a%p; a=1ll*a*a%p; b>>=1; } return res; }//快速幂 int c(int a,int b,int p) { if(b>a) return 0; int res=1; for(int i=1,j=a; i<=b; i++,j--) { res=res*j%p; res=res*ksm(i,p-2,p)%p; } return res; } int lucas(int a,int b,int p) { if(a<p &&b<p) return c(a,b,p); return c(a%p,b%p,p)*lucas(a/p,b/p,p)%p; }
const int N = 1010; int C[N][N]; void init() { C[0][0] = 1; for (int i = 1; i < N; i++) { C[i][0] = 1;//初始化 for (int j = 1; j <= i; j++) { C[i][j] = C[i-1][j] + C[i-1][j-1]; //对于最后一位数取或不取的情况都要考虑 C[i][j] %= mod; } } }
signed main() { init(); int k=rd(); vector<int> cnt(k + 1, 0), sum(k + 1, 0); vector<int> f(k + 1); //动态减少空间时间 int n = 0; for (int i = 1; i <= k; i++) { cnt[i]=rd(); sum[i] += sum[i-1] + cnt[i]; } f[1] = 1; for (int i = 2; i <= k; i++) { // f[i] = f[i-1] * C[sum[i-1] + cnt[i] - 1][cnt[i] - 1];//暴力方法 f[i]=f[i-1]*lucas(sum[i-1]+cnt[i]-1,cnt[i]-1,mod);//不怎么暴力但慢一点的方法 f[i] %= mod; } printf("%lld\n",f[k]); return 0; return 0; }
标签:题意 bsp sum force 空间 题目 初始化 解法 const
原文地址:https://www.cnblogs.com/firerunner/p/14656580.html