版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/luyehao1/article/details/81938264
题目链接:
题意:
将大小为1 - nm的数填入n*m的矩阵中,问只有有一个纳什均衡点的情况数。纳什均衡点要求这个数在其所在行列中均为最大值。
思路:
因为nm必然大于其余所有值,所以一定是nm所在位置为纳什均衡点。那么第二大的数只能在nm所在的行列中,同理第三大的数只能在前两个数所在的行列中。因此,我们可以从nm - 1这个顺序去考虑。
定义:dp[i][j][k]:第 i 个数(nm-i+1)放好后有 j 行已经有数字了,有 k 列已经有数字了。
状态转移:
行+1:有 k*(n-j+1) 种放法
列+1:有 j*(m-k+1) 种放法
行列数不变:有 jk-i+1 种放法
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <vector>
#include <set>
#include <queue>
#include <algorithm>
using namespace std;
typedef long long ll;
const int MAX = 1e4 + 10;
int n,m;
ll mod;
int dp[85*85][85][85];
int main()
{
int T;
scanf("%d", &T);
while(T--)
{
scanf("%d%d%lld",&n,&m,&mod);
memset(dp,0,sizeof(dp));
dp[1][1][1]=n*m;
for(int i=2;i<=n*m;i++){
for(int j=1;j<=n;j++){
for(int k=1;k<=m;k++){
if(j*k>=i){
dp[i][j][k]=(dp[i][j][k]+1ll*dp[i-1][j-1][k]*k*(n-j+1))%mod;
dp[i][j][k]=(dp[i][j][k]+1ll*dp[i-1][j][k-1]*j*(m-k+1))%mod;
dp[i][j][k]=(dp[i][j][k]+1ll*dp[i-1][j][k]*(j*k-i+1))%mod;
}
}
}
}
printf("%lld\n",dp[n*m][n][m]);
}
return 0;
}