Cheerleaders UVA - 11806 计数问题

In most professional sporting events, cheerleaders play a major role in entertaining the spectators. Their

roles are substantial during breaks and prior to start of play. The world cup soccer is no exception.

Usually the cheerleaders form a group and perform at the centre of the eld. In addition to this group,

some of them are placed outside the side line so they are closer to the spectators. The organizers would

like to ensure that at least one cheerleader is located on each of the four sides. For this problem, we

will model the playing ground as an

M

N

rectangular grid. The constraints for placing cheerleaders

are described below:

There should be at least one cheerleader on each of the four sides. Note that, placing a cheerleader

on a corner cell would cover two sides simultaneously.

There can be at most one cheerleader in a cell.

All the cheerleaders available must be assigned to a cell. That is, none of them can be left out.

The organizers would like to know, how many ways they can place the cheerleaders while maintaining

the above constraints. Two placements are different, if there is at least one cell which contains a

cheerleader in one of the placement but not in the other.

Input

The rst line of input contains a positive integer

T

50, which denotes the number of test cases.

T

lines then follow each describing one test case. Each case consists of three nonnegative integers, 2

M

,

N

20 and

K

500. Here

M

is the number of rows and

N

is the number of columns in the grid.

K

denotes the number of cheerleaders that must be assigned to the cells in the grid.

Output

For each case of input, there will be one line of output. It will rst contain the case number followed by

the number of ways to place the cheerleaders as described earlier. Look at the sample output for exact

formatting. Note that, the numbers can be arbitrarily large. Therefore you must output the answers

modulo

1000007.

Sample Input

2

2 2 1

2 3 2

Sample Output

Case 1: 0

Case 2: 2

简单的计数问题;

题目所说:第一行,最后一行,第一列,最后一列都得有石子;

设集合A:不在第一行,

集合B:不在最后一行;

集合C:不在第一列;

集合D:不在最后一列;

总集合为S的话,那么我们要求的就是在S中而且不在集合ABCD中的个数;

那我们用二进制来表示,总的数量为2^4=16种情况;

容斥一下就Ok了;

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstdlib>
#include<cstring>
#include<string>
#include<cmath>
#include<map>
#include<set>
#include<vector>
#include<queue>
#include<bitset>
#include<ctime>
#include<deque>
#include<stack>
#include<functional>
#include<sstream>
//#include<cctype>
//#pragma GCC optimize(2)
using namespace std;
#define maxn 2000005
#define inf 0x7fffffff
//#define INF 1e18
#define rdint(x) scanf("%d",&x)
#define rdllt(x) scanf("%lld",&x)
#define rdult(x) scanf("%lu",&x)
#define rdlf(x) scanf("%lf",&x)
#define rdstr(x) scanf("%s",x)
typedef long long  ll;
typedef unsigned long long ull;
typedef unsigned int U;
#define ms(x) memset((x),0,sizeof(x))
const long long int mod = 1e6 + 7;
#define Mod 1000000000
#define sq(x) (x)*(x)
#define eps 1e-4
typedef pair<int, int> pii;
#define pi acos(-1.0)
//const int N = 1005;
#define REP(i,n) for(int i=0;i<(n);i++)
typedef pair<int, int> pii;
inline ll rd() {
	ll x = 0;
	char c = getchar();
	bool f = false;
	while (!isdigit(c)) {
		if (c == ‘-‘) f = true;
		c = getchar();
	}
	while (isdigit(c)) {
		x = (x << 1) + (x << 3) + (c ^ 48);
		c = getchar();
	}
	return f ? -x : x;
}

ll gcd(ll a, ll b) {
	return b == 0 ? a : gcd(b, a%b);
}
int sqr(int x) { return x * x; }

/*ll ans;
ll exgcd(ll a, ll b, ll &x, ll &y) {
	if (!b) {
		x = 1; y = 0; return a;
	}
	ans = exgcd(b, a%b, x, y);
	ll t = x; x = y; y = t - a / b * y;
	return ans;
}
*/

int c[503][503];
int n, m, k;
void init() {
	c[0][0] = 1;
	for (int i = 0; i <= 503; i++) {
		c[i][0] = c[i][i] = 1;
		for (int j = 1; j < i; j++)c[i][j] = (c[i - 1][j] + c[i - 1][j - 1]) % mod;
	}
}

int main() {
//	ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
	int T; cin >> T;
	init(); int tot = 0;
	while (T--) {
		tot++;
		cin >> n >> m >> k;
		cout << "Case " << tot << ": ";
		int sum = 0;
		for (int i = 0; i < 16; i++) {
			int bk = 0;
			int r = n, C = m;
			if (i & 1) { bk++; r--; }
			if (i & 2) { bk++; r--; }
			if (i & 4) { bk++; C--; }
			if (i & 8) { bk++; C--; }
			if (bk % 2) {
				sum = (sum + mod - c[C*r][k]) % mod;
			}
			else sum = (sum + c[C*r][k]) % mod;
		}
		cout << sum << endl;
	}
	return 0;
}

原文地址:https://www.cnblogs.com/zxyqzy/p/10322942.html

时间: 2024-10-19 23:03:16

Cheerleaders UVA - 11806 计数问题的相关文章

G - Cheerleaders (UVA - 11806)

- 题目大意 本题大致意思是讲:给定一个广场,把它分为M行N列的正方形小框.现在给定有K个拉拉队员,每一个拉拉队员需要站在小框内进行表演.但是表演过程中有如下要求: (1)每一个小框只能站立一个拉拉队员: (2)广场的第一行,最后一行,第一列,最后一列都至少站有一个拉拉队员: (3)站在广场的四个角落的拉拉队员可以认为是同时占据了一行和一列. - 解题思路 利用容斥原理来解决,将不满足条件的一一剔除,(我的方法比较笨重,如果选择二进制来判断做起来就比较轻松了). - 代码 #include<io

UVA - 11806 - Cheerleaders (递推)

UVA - 11806 Cheerleaders Time Limit: 2000MS Memory Limit: Unknown 64bit IO Format: %lld & %llu Submit Status Description C Cheerleaders In most professional sporting events, cheerleaders play a major role in entertaining the spectators. Their roles a

uva 11806 - Cheerleaders(容斥原理)

题目链接:uva 11806 - Cheerleaders 题目大意:在一个m行n列的矩阵网里放k个石子,问有多少种画法?每个格子最多放一个石子,所有石子必须用完,并且在第一行.最后一行.第一列和最后一列都得有石子. 解题思路:容斥原理,我们可以先求说在m?n的矩阵上放k个石子的种数C(nmk),减掉四条边界不放的情况就是答案了.所以枚举16种状态,用二进制数表示说四条边中那些边是不放石子的. 代码 #include <cstdio> #include <cstring> cons

UVA 11806 - Cheerleaders(数论+容斥原理)

题目链接:11806 - Cheerleaders 题意:在一个棋盘上,要求四周的四行必须有旗子,问有几种摆法. 思路:直接算很容易乱掉,利用容斥原理,可知AUBUCUD = |A| + |B| + |C| + |D| - |AB| - |BC| - |AC| - |AD| - |BD| - |CD| + |ABC| + |ABD| + |ACD| + |BCD| - |ABCD| 由此利用位运算去计算即可 代码: #include <stdio.h> #include <string.

UVa 11806 Cheerleaders

题意:m行n列的矩形网格放k个相同的石子,要求第一行最后一行第一列最后一列都必须有石子,问有多少种放法 A为第一行没有石子的方案数,BCD依此类推,全集为S 如果没有任何要求的话,放法数应该是C(rc, k) 解法中利用容斥原理来解 所求的方案就是在S中但不在ABCD中任何一个的方案即:S - |A∪B∪C∪D| 而|A∪B∪C∪D| = |A| + |B| + |C| + |D| - |A∩B| - |A∩C| - |A∩D| - |B∩C| - |B∩D| - |C∩D| + |A∩B∩C|

【递推】【组合数】【容斥原理】UVA - 11806 - Cheerleaders

http://www.cnblogs.com/khbcsu/p/4245943.html 本题如果直接枚举的话难度很大并且会无从下手.那么我们是否可以采取逆向思考的方法来解决问题呢?我们可以用总的情况把不符合要求的减掉就行了. 首先我们如果不考虑任何约束条件,我们可以得出如下结论:                                                                       下载我们假定第一行不站拉拉队员的所有的站立方法有A种.最后一行不站拉拉队员的

uva 11806 - Cheerleaders(容斥原理+二进制)

题目链接点击打开链接 题意: n行m列网格放k个石子.有多少种方法?要求第一行,第一列,最后一行,最后一列必须有石子. 思路: 1.利用容斥原理的拓展 假设有三个集合 S 另有三个集合A B C,不属于 A.B.C任何一个集合,但属于全集S的元素, 奇数个减:偶数个加 此处是S为空集  A.B.C.D分别代表 行 列中的四种情况: AUBUCUD = |A| + |B| + |C| + |D| - |AB| - |BC| - |AC| - |AD| - |BD| - |CD| + |ABC| +

UVA - 11806 Cheerleaders (容斥原理)

题意:在N*M个方格中放K个点,要求第一行,第一列,最后一行,最后一列必须放,问有多少种方法. 分析: 1.集合A,B,C,D分别代表第一行,第一列,最后一行,最后一列放. 则这四行必须放=随便放C[N * M][K] - 至少有一行没放,即ABCD=随便放-A的补集 ∪ B的补集 ∪ C的补集 ∪ D的补集. 2.A的补集 ∪ B的补集 ∪ C的补集 ∪ D的补集,可用容斥原理计算,二进制枚举即可. #include<cstdio> #include<cstring> #incl

uva 11806 Cheerleaders(容斥)

题意:如何摆放拉拉队的问题,在矩形网格m*n中,k名拉拉队员,要求四周网格中each side有至少一名拉拉队员,corner有人算两边,问有多少种摆法? 思路:容斥: c[m*n][k] -- c[(n-1)*m][k] U c[(n-1)*m][k] U c[n*(m-1)][k] U c[n*(m-1)][k] #include<cstdio> #include<iostream> #include<cstring> #define mod 1000007 usi