给出由大写字母组成的字符串s
,即从“ A”到“ Z”。我们必须找出多少个字符串t
的长度等于s
的长度,并且这些字符串也由大写字母组成,并且满足以下条件:
t
在字典上比字符串s
大。s
和t
时,t
的字典顺序仍然大于s
。找出此类字符串t
。这是我在使用dp的特定社论中找到的解决方案:
让F [i] [ok1] [ok2]是如果已经获得字符串T的前i-1个字符且ok1和ok2表示以下信息,则可以生成的字符串T的数目:
ok1 = 0表示T的前i-1个字符仍与S的对应t-1字符匹配。ok1 = 1表示T大于S。
ok2 = 0表示按相反的顺序,T中的前t-1个字符在字典上已经大于S中的相应字符。否则,ok2 =0。
令N为S的长度。当然,结果将为F [0] [0] [0]。我们可以用F [N + 1] [1] [1] = 1来初始化dp。我们将按i的降序计算F。对于每个i,ok1,ok2,我们尝试将所有可能的字符放在位置i上,以使T的字典顺序从不小于原始顺序的S:
//let s is 0-indexed
for (int i = N - 1; i > 0; i--)
for (int ok1 = 0; ok1 <= 1; ok1++)
for (int ok2 = 0; ok2 <= 1; ok2++) {
//make sure that T is always lexicographically larger than S in original order
for (char c = ok1 == 0 ? s* : 'A'; c <= 'Z'; c++) {
int nextOk2 = ok2;
if (c != s[pos]) {
//if we put a character c > s[pos] in position pos of T then T became lexicographically larger than S in reversed order
nextOk2 = c > s[pos];
}
f[pos][ok1][ok2] = (f[pos][ok1][ok2] + f[pos + 1][ok1 || c > s[pos]][nextOk2]) % MOD;
}
}
复杂度将为O(N×2×2×26)。