题目描述
给你一个长度为50的数字串,问你有多少个子序列构成的数字可以被3整除
答案对1e9+7取模
输入描述:
输入一个字符串,由数字构成,长度小于等于50
输出描述:
输出一个整数
这个题使用动态规划,dp[i][j]的i表示为前i个数的包括第i个数的所有序列,j表示为余数的个数。
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<vector>
#include<string>
#include<cstring>
using namespace std;
int main() {
string s;
cin >> s;
long long int dp[51][3];
memset(dp, 0, sizeof(dp));
int t = (s[0] - '0') % 3;
dp[0][t] = 1;
for (int i = 1; i < s.size(); i++) {
int t = (s[i] - '0') % 3;
if (t == 0) {
dp[i][0] = (dp[i - 1][0]*2 + 1) % 1000000007;
dp[i][1] = (dp[i - 1][1]*2) % 1000000007;
dp[i][2] = (dp[i - 1][2]*2) % 1000000007;
}
else if (t == 1) {
dp[i][0] = (dp[i - 1][0] + dp[i - 1][2]) % 1000000007;
dp[i][1] = (dp[i - 1][1] + dp[i - 1][0] + 1) % 1000000007;
dp[i][2] = (dp[i - 1][1] + dp[i - 1][2]) % 1000000007;
}
else {
dp[i][0] = (dp[i - 1][1] + dp[i - 1][0]) % 1000000007;
dp[i][1] = (dp[i - 1][1] + dp[i - 1][2]) % 1000000007;
dp[i][2] = (dp[i - 1][2] + dp[i - 1][0] + 1) % 1000000007;
}
}
cout << dp[s.size() - 1][0] % 1000000007;
return 0;
}