hdu 6114 百度之星复赛B T1
Chess
Problem Description
車是中国象棋中的一种棋子,它能攻击同一行或同一列中没有其他棋子阻隔的棋子。
一天,小度在棋盘上摆起了许多車……他想知道,在一共N×M个点的矩形棋盘中摆最多个数的車使其互不攻击的方案数。
他经过思考,得出了答案。
但他仍不满足,想增加一个条件:对于任何一个車A,
如果有其他一个車B在它的上方(車B行号小于車A),那么車A必须在車B的右边(車A列号大于車B)。
现在要问问你,满足要求的方案数是多少。
Input
第一行一个正整数T,表示数据组数。
对于每组数据:一行,两个正整数N和M(N<=1000,M<=1000)。
对于每组数据:一行,两个正整数N和M(N<=1000,M<=1000)。
Output
对于每组数据输出一行,代表方案数模1000000007(1e9+7)。
Sample Input
1
1 1
Sample Output
1
——————————————————————————————————————————
这道题很明显必然有行或者列是满的 行列交换答案不变 所以我们可以强制列大于行
那么因为各个位置的相对关系是固定的 所以我们在n列里面选m行之后答案是唯一的
所以问题就转换成了n列选m列 即C(n,m)
#include<cstdio> #include<cstring> #include<algorithm> #define LL long long using namespace std; const int mod=1000000007; int T,n,m,ans; LL c[1005][1005]; LL C(int x,int y) { if(y==x||y==0)return 1; if(y==1)return x; if(c[x][y])return c[x][y]%mod; c[x][y]=(C(x-1,y-1)+C(x-1,y))%mod; return c[x][y]; } int main() { scanf("%d",&T); while(T--){ scanf("%d %d",&n,&m); printf("%I64d\n",C(max(n,m),min(n,m))); } return 0; }