CDOJ 1805 矩阵

Description

小明发现了一种特殊的N×M的矩阵,矩阵里的元素都是1−1。假设Ai为第 i 行 (1 ≤ i ≤ N) 所有元素的乘积,Bj 为第 j 列 (1 ≤ j ≤ M) 所有元素的乘积。喜欢搞事情的小明突发奇想,想知道有多少个不相同的,大小为N×M的矩阵使得所有Ai, Bj都是K的矩阵(K=1 或者 -1)。
当且仅当两个矩阵存在一个元素不相同时两个矩阵不相同。

Standard Input

输入只有一行,三个数字N, M, K.

Standard Output

输出一个数字,即满足条件的不同矩阵的数量.

Samples

Input Output
2 2 1 2

Note

这两个不同的矩阵分别是
1 1
1 1

-1 -1
-1 -1

题意

要求构造NxM的矩阵,使得每一行的乘积均为k,每一列的乘积均为k,其中k只可能是-1和1

题解1

首先,这个矩阵肯定只能是1和-1组成的矩阵了
k为1,那么每一列只能有偶数个-1;若k为-1,那么每一列只能有奇数个-1
那么对于每一列(长度为N),都有2N−1种可能的选择
那么,假设前M−1列都构造完毕,最后一列呢?
显然,如果第1行已经有x个-1,那么最后一列的第1行应该是一个使得该行有奇数个-1(对应k=-1)或偶数个-1(对应k=1)的数,显然也可以确定
这样,整个矩阵都可以构建完成,可见这个矩阵的确定只与前M-1列有关,一共有 2(N−1)(M−1)个矩阵
那么问题来了:N行的乘积为k了,前M-1列的乘积也为k了,那么第M列的乘积呢?
讨论如下
k=1:若前M-1列构成的矩阵第i行乘积为-1,那么第M列第i行也是-1;若为1,那么第i行也是1;既然如此,那么说明第M列元素的乘积等于前M-1列的所有行的乘积,后者等价于所有列的乘积,故第M列的乘积为1
k=-1:若前M-1列构成的矩阵第i行乘积为-1,那么第M列第i行1;若为1,那么第i行是-1;既然如此,那么说明第M列元素的乘积等于前M-1列的所有行的乘积的相反数的乘积,后者等于所有数的乘积再乘以(−1)N(N为行数),等价于前M-1列的乘积乘上(−1)N,也就是说最后一列的乘积为(−1)M−1·(−1)N
N×(M−1)为偶数,最后一列乘积为1
N×(M−1)为奇数,最后一列乘积为-1
其余结论显然

#include
// 代码已精简
int main(){
	int m, n, k;
    scanf("%d%d%d", &n, &m, &k);
	if(k == -1 && (m + n) % 2){
		putchar('0');
		return 0;
	}
	printf("%llu", 1ull << (--m*--n));
	return 0;
}

  1. https://www.cnblogs.com/scidylanpno/p/7978086.html ↩︎

你可能感兴趣的:(算法)