解析:关于题意的理解参考:点击打开链接
设dp[i][j] 为考虑前i个位置且高度小于第i个位置的人数为j的方案数。
状态转移方程:
dp[i][j] = i&1? sigma(dp[i-1][j-k]):sigma(dp[i-1][j+k])
[code]:
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
typedef unsigned long long LL;
int n,m;
LL dp[55][55];
int main(){
int i,j,k,cas;
scanf("%d",&cas);
for(int T=1;T<=cas;T++){
scanf("%d%d",&n,&m);
memset(dp,0,sizeof(dp));
printf("Case %d: ",T);
if(m==1&&n<=4){
puts("1");
}else{
if(m==1) n--,m=2;
dp[1][m-1] = 1;
for(i = 2;i <= n;i++){
for(j = 0;j <= n-i;j++){
dp[i][j] = 0;
if(i&1){
for(k = 0;k <= j&&j-k<=n-i+1;k++)
dp[i][j] += dp[i-1][j-k];
}else{
for(k = 1;k <= n-j&&j+k<=n-i+1;k++)
dp[i][j] += dp[i-1][j+k];
}
}
}
printf("%llu\n",dp[n][0]);
}
}
return 0;
}