题目大意:给一个字符串,第i个字符表示第i列的皇后所在的位置,如果该字符为?,表示该皇后可以在该列的任意行,反之,则限定了该皇后的拜访位置,为几就表示放在第几行,求棋盘每列都放满皇后有多少种情况,这里的皇后和以前的皇后不一样,如果该列放了皇后,则该列就不能再放皇后,且以皇后为中心的九宫格也不能放皇后
解题思路:用dp[i][j]表示第i行第j列放皇后的情况有几种,当fabs(k-i) > 1时,dp[i][j] += dp[k][j-1],因为只有满足这种情况,第j列第i行才能放置皇后,所以要初始化第1列,如果第一列为'?',则第一列的每行都可以拜访皇后,反之,如果不为‘?’,就只将改行的状态设置成1,然后递推下去
#include<cstdio>
#include<cstring>
#define maxn 20
long long dp[maxn][maxn];
char str[maxn];
int main() {
while(scanf("%s",str) != EOF) {
int len = strlen(str);
int temp;
for(int i = 1; i <= len; i++)
for(int j = 1; j <= len; j++)
dp[i][j] = 0;
if(str[0] == '?') {
for(int i = 1; i <= len; i++)
dp[i][1] = 1;
}
else {
if(str[0] >= '1' && str[0] <= '9')
temp = str[0] - '0';
else
temp = str[0] - 'A' + 10;
dp[temp][1] = 1;
}
for(int i = 2; i <= len; i++)
if(str[i-1] == '?') {
for(int j = 1; j <= len ;j++) {
for(int k = j - 2; k >= 1; k--)
dp[j][i] += dp[k][i-1];
for(int k = j + 2; k <= len; k++)
dp[j][i] += dp[k][i-1];
}
}
else {
if(str[i-1] >= '1' && str[i - 1] <= '9')
temp = str[i-1] - '0';
else
temp = str[i-1] - 'A' + 10;
for(int k = temp - 2; k >= 1; k--)
dp[temp][i] += dp[k][i-1];
for(int k = temp + 2; k <= len; k++)
dp[temp][i] += dp[k][i-1];
}
long long sum = 0;
for(int i = 1; i <= len; i++)
sum += dp[i][len];
printf("%lld\n",sum);
}
return 0;
}