ACM-ICPC2018江苏站 E.Message

链接

https://nanti.jisuanke.com/t/28869

题解

我看的题解:https://blog.csdn.net/MIECZ/article/details/80591212
有个问题他没说,就是每种不合法方案如何与已经统计的方案构造一一对应关系?
只有你构造出了一一对应关系,才能相减,因为这个减法的实质是从一个全集中减去一个子集
A=Cn2n+m4Cm2n+m4 A = C n + m − 4 n − 2 C n + m − 4 m − 2 B=Cn1n+m4Cm1n+m4 B = C n + m − 4 n − 1 C n + m − 4 m − 1
答案 ans=AB a n s = A − B
对于一种在 A A 中存在的,路线相交的方案,我考虑图形相同的方案集合,这个集合中,我选择最后一个交点,调换两条路径的走向,那么就能够构造出一种在B中统计过的方案,而且这样肯定能够构造出 B B 中符合这种图形的全部方案。
既然对于每种图形,它在A B B <script type="math/tex" id="MathJax-Element-1250">B</script>中对应的路径数相同,所以相减也就没问题了
这题其实最后减去的不是子集,但是构造出一种和子集一一对应的路径集合,这也是很巧妙了

代码

//组合数
#include <cstdio>
#include <algorithm>
#include <cctype>
#include <cstring>
#define maxn 2018
#define ll long long
#define mod 1000000007ll
using namespace std;
ll frac[maxn], _frac[maxn], N, M, f[maxn];
ll fastpow(ll a, ll b)
{
    ll t, ans=1;
    for(t=a;b;b>>=1,t=t*t%mod)if(b&1)ans=ans*t%mod;
    return ans;
}
ll C(ll n, ll m)
{
    return frac[n]*_frac[m]%mod*_frac[n-m]%mod;
}
void init()
{
    ll i, j;
    frac[0]=_frac[0]=1;
    for(i=1;i<=2000;i++)frac[i]=frac[i-1]*i%mod, _frac[i]=fastpow(frac[i],mod-2);
}
int main()
{
    ll ans;
    init();
    while(~scanf("%lld%lld",&N,&M))
    {
        if(N==2 or M==2)ans=1;
        else ans=C(N+M-4,M-2)*C(N+M-4,N-2)%mod-C(N+M-4,M-1)*C(N+M-4,N-1)%mod;
        printf("%lld\n",(ans%mod+mod)%mod);
    }
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值