[BZOJ4870][SHOI2017]组合数问题 DP+矩阵快速幂
2017-11-01 07:53
537 查看
考虑这个式子的组合意义,表示从nk个物品中选取mod k=r个物品。递推式很显然咯,f[i][j]=f[i-1][j]+f[i-1][(j-1)%k]。矩阵快速幂加速一下就好了。
WA点:转移矩阵第i行是第j列和(j-1)%k列为一,所以第0行是第0列和k-1列,特别地,当k=1时,1*1矩阵中那个唯一的数应该是2,因为加了两次。
代码:
WA点:转移矩阵第i行是第j列和(j-1)%k列为一,所以第0行是第0列和k-1列,特别地,当k=1时,1*1矩阵中那个唯一的数应该是2,因为加了两次。
代码:
#include<iostream> #include<cstdio> #include<cstring> #define ll long long using namespace std; ll n,r,K,mod; struct matrix { ll a[51][51]; matrix(){memset(a,0,sizeof(a));} matrix operator *(const matrix &x) { matrix ans; for(int i=0;i<K;i++) for(int j=0;j<K;j++) for(int k=0;k<K;k++) ans.a[i][j]=(ans.a[i][j]+a[i][k]*x.a[k][j]%mod)%mod; return ans; } }m; matrix ksm(matrix a,ll b) { matrix re; for(int i=0;i<K;i++) re.a[i][i]=1; for(;b;b>>=1) { i fa97 f(b&1) re=re*a; a=a*a; } return re; } int main() { scanf("%lld%lld%lld%lld",&n,&mod,&K,&r); m.a[0][0]+=1;m.a[0][K-1]+=1; for(int i=1;i<K;i++) m.a[i][i]=m.a[i][i-1]=1; m=ksm(m,n*K); printf("%lld",m.a[0][r]); return 0; }
相关文章推荐
- 【jzoj5215】【BZOJ4870】【Shoi2017】【GDOI2018模拟7.9】【组合数问题】【矩阵快速幂】
- [BZOJ4870][Shoi2017]组合数问题 dp+矩阵乘
- 【bzoj4870】[Shoi2017]组合数问题 dp+快速幂/矩阵乘法
- BZOJ 4870 [Shoi2017] 组合数问题
- 【BZOJ4870】[Shoi2017]组合数问题 动态规划(矩阵乘法)
- BZOJ4870: [Shoi2017]组合数问题
- [bzoj4870] [Shoi2017]组合数问题
- bzoj4870 [Shoi2017]组合数问题(dp+矩阵倍增)
- [bzoj4870][Shoi2017]组合数问题
- bzoj 4870: [Shoi2017]组合数问题 动态规划
- bzoj 4870: [Shoi2017]组合数问题 [矩阵乘法优化dp]
- BZOJ4870: [Shoi2017]组合数问题
- bzoj 4870: [Shoi2017]组合数问题
- BZOJ4870:[SHOI2017]组合数问题——题解
- BZOJ4870 [Shoi2017]组合数问题 【组合数 + 矩乘】
- BZOJ 4870 [Shoi2017]组合数问题 ——动态规划 矩阵乘法
- jzoj5215&&bzoj4870[Shoi2017]组合数问题 dp+矩阵快速幂
- BZOJ_4870_[Shoi2017]组合数问题_矩阵乘法
- bzoj4870 [Shoi2017]组合数问题
- bzoj4870: [Shoi2017]组合数问题(DP+矩阵乘法优化)