1 条题解
-
0
显然, 必须为偶数,不为偶数输出 。
我们注意到部分分 ,先解决这个部分。
分成 种情况。
情况一 。
显然,我们需要将 个来回塞进前面 个来回中。这个就是 个不同盒子, 个相同的球。
为了使转变方向次数越少,我们必须尽可能最大化同一方向的数量。转化一下变成让盒子数量尽可能多。再贪心转化一下变成每个盒子非空。先将每个盒子扔个球,再隔板法就行了,方案为 。
情况二 。
同上,我们要使空盒子数量尽可能少,那么只能有 个空盒子,每个盒子只能填 或 个球,总方案 。
再考虑 的情况,假设从 到 的点,都可以看成是新的 到 的情况,我们直接套用上面的解法,求个积就行了。
的情况同理,每次 到 就是一个新的 到 ,所以是独立的。
代码
#include<bits/stdc++.h> #define int long long #define endl "\n" using namespace std; namespace did{ int mod=1e9+7; int power(int a,int b){ int ans=1; while(b){ if(b&1)ans=(ans*a)%mod; a=(a*a)%mod; b>>=1; } return ans; } int jc[1000006],inv[1000006]; void init(){ jc[0]=1; for(int i=1;i<=1000000;i++)jc[i]=(jc[i-1]*i)%mod; inv[1000000]=power(jc[1000000],mod-2); for(int i=1000000;i>=1;i--)inv[i-1]=(inv[i]*i)%mod; } int C(int x,int y){ if(x<y||x<0||y<0)return 0; return ((jc[x]*inv[y])%mod*inv[x-y])%mod; } int n; int a[1000006]; void lusolve(){ cin>>n; for(int i=1;i<=n;i++){ cin>>a[i]; if(a[i]&1)return cout<<0,void(); } int ans=1; for(int i=1;i<n;i++){ if(a[i]>=a[i+1]){ ans*=C(a[i]/2,a[i+1]/2); }else ans*=C(a[i+1]/2-1,a[i]/2-1); ans%=mod; } cout<<ans; } } signed main(){ int Q=1; did::init(); while(Q--)did::lusolve(); return 0; }时间复杂度 。
- 1
信息
- ID
- 7594
- 时间
- 2000ms
- 内存
- 256MiB
- 难度
- 6
- 标签
- 递交数
- 17
- 已通过
- 10
- 上传者