
动态规划
创建(len + 1) * n的二维数组dp[][],其中dp[i][j]表示前i位数中对n整除余数为j的可能的前i位数值总数,len表示数字的长度,则把数组dp[][]的所有元素的值都算出来,其中dp[len][0]即为所求答案。首先,把dp[1][i],i = 0, 1, 2, ..., n - 1求出来,然后dp[i][newj] += dp[i - 1][j],其中newj = (10 * j + k[i + 1] - '0') % n。
#include <iostream>
using namespace std;
int main(void)
{
char k[100];
int n, len;
cin >> k;
cin >> n;
len = strlen(k); //数字k的长度
int** dp = new int* [len + 1]; //创建(len + 1) * n的二维数组dp[][],其中dp[i][j]表示前i位数中对n整除余数为j的可能的前i位数值总数
for (int i = 0; i < len + 1; i++)
dp[i] = new int[n];
for (int i = 0; i < len + 1; i++) //初始化,使数组的所有元素都为0
{
for (int j = 0; j < n; j++)
dp[i][j] = 0;
}
//求dp[1][i],i = 0, 1, 2, ..., n - 1
if (k[0] == 'X') //当最高位数为‘X’时
{
for (int i = 0; i <= 9; i++) //对‘X’的所有可能取值都考虑进去
{
dp[1][i % n]++;
}
}
else //当最高位为确定的数时
{
int num = k[0] - '0';
dp[1][num % n]++;
}
for (int i = 1; i < len; i++)
{
for (int j = 0; j < n; j++)
{
if (k[i + 1] == 'X')
{
int newj;
for (int m = 0; m <= 9; m++)
{
newj = (10 * j + m) % n;
dp[i + 1][newj] += dp[i][j]; //转移矩阵
}
}
else
{
int newj = (10 * j + k[i + 1] - '0') % n;
dp[i + 1][newj] += dp[i][j];
}
}
}
cout << dp[len][0] << endl;
return 0;
}
运行结果:

1268

被折叠的 条评论
为什么被折叠?



