【Luogu P1350】车的放置

链接:

题目

博客园

题目大意:

给定一个畸形的方块,求在上面放 \(k\) 个车能让它们互不相吃的方案数。

正文:

我们知道,车能够吃掉它这一行和一列的棋子,先来处理吃一行的情况。其实这个特别简单,在枚举的时候每一行只算一个棋子的就好了。

再处理列的情况。我们设 \(f_{i,j}\) 表示 \(i\) 行里一共有 \(j\) 个车的方案数。每次处理时,第 \(i\) 行就是第 \(i-1\) 行的方案数乘上这一行还可以放的位置个数。那么这个位置个数是什么呢?因为前 \(i-1\) 行放了 \(j-1\) 互不相吃的棋子(也就是每列只有一个车),那如果我们还要在第 \(i\) 行放一个,它就只能放在剩下的位置,也就是 \(m - (j - 1)\) 个位置,其中的 \(m\) 表示第 \(i\) 行的格子个数。

也就是说转移方程为:

\[f_{i,j}=f_{i-1,j-1}\times (m-j+1)+f_{i-1,j} \]

后面还加个 \(f_{i-1,j}\) 是因为第 \(i\) 行还可以不放任何车。

代码:

	for (int i = 0; i <= b + d; i++) f[i][0] = 1;
	for (int i = 1; i <= b + d; i++)
	{
		for (int j = 1; j <= k; j++)
		{
			if (i <= b && j > a) break;
			f[i][j] += f[i - 1][j];
			if (i <= b) (f[i][j] += f[i - 1][j - 1] * (a - j + 1) % mod) %= mod; 
			else (f[i][j] += f[i - 1][j - 1] * (a + c - j + 1) % mod) %= mod; 
		}
	}
	printf("%d\n", f[b + d][k]);
posted @ 2020-12-12 07:43  Jayun  阅读(49)  评论(0编辑  收藏  举报