[hdu6482]A Path Plan

A Path Plan

题解

很容易发现,如果两个起点与终点的连线相交时,即[x1>x2]\not =[y1>y2]时,无论怎么走都是一定会相交的。因此我们只需考虑[x1>x2]=[y1>y2]的情况。

不妨设x1<x2,如果会相交的话,路径一定是这样的

两者一定会相交于一个点,我们尝试将它们的终点互换一下,就成了这样

可以发现,任意一条会相交的路径相当于从y1\rightarrow x2,y2\rightarrow x1的合法方案数。

于是答案就是从C_{x1+y1}^{x1}C_{x2+y2}^{x2}-C_{x1+y2}^{x1}C_{x2+y1}^{x2}

源码

#include<cstdio>
#include<cmath>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#include<vector>
#include<queue>
#include<map>
#include<set>
using namespace std;
#define MAXN 200005
typedef long long LL;
const int mo=1e9+7;
#define gc() getchar()
template<typename _T>
void read(_T &x){
	_T f=1;x=0;char s=gc();
	while(s>'9'||s<'0'){if(s=='-')f=-1;s=gc();}
	while(s>='0'&&s<='9'){x=(x<<3)+(x<<1)+(s^48);s=gc();}
	x*=f;
}
int fac[MAXN],inv[MAXN],f[MAXN];
void init(){
	fac[0]=inv[0]=fac[1]=inv[1]=f[1]=1;
	for(int i=2;i<=2e5;i++){
		fac[i]=1ll*fac[i-1]*i%mo;
		f[i]=1ll*(mo-mo/i)*f[mo%i]%mo;
		inv[i]=1ll*inv[i-1]*f[i]%mo;
	}
}
int C(int x,int y){
	if(x<0||y<0||x<y)return 0;
	return 1ll*fac[x]*inv[y]%mo*inv[x-y]%mo;
}
int main(){
	int t;read(t);init();
	while(t--){
		int x1,x2,y1,y2;
		read(x1);read(x2);read(y1);read(y2);
		if(x1>x2)swap(x1,x2),swap(y1,y2);
		if(y1>y2)puts("0");
		else printf("%d\n",(mo+1ll*C(x1+y1,x1)*C(x2+y2,x2)%mo-1ll*C(x1+y2,x1)*C(x2+y1,x2)%mo)%mo);
	}
	return 0;
}

谢谢!!!

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值