直接上代码:
求得结果 :3616159
import java.util.Arrays;
import java.util.Scanner;
public class 本质上升递增子序列 {
public static void main(String[] args) {
String s = "tocyjkdzcieoiodfpbgcncsrjbhmugdnojjd"
+ "dhllnofawllbhfiadgdcdjstemphmnjihecoapdjjrprrqnh"
+ "gccevdarufmliqijgihhfgdcmxvicfauachlifhafpdccfse"
+ "flcdgjncadfclvfmadvrnaaahahndsikzssoywakgnfjjaihtniptwoulxbaeqkqhfwl";
char[] tmp = s.toCharArray();
int[] dp = new int[s.length()]; //dp[i]代表以s[i]结尾的本质不同递增子序列个数。注意是个数。
Arrays.fill(dp, 1); //因为每个字符自身可以看作递增的,所以初始化为1。
for(int i = 0; i < tmp.length; ++i) {
for(int j = 0; j < i; ++j) { //dp[i]递增子序列的个数,肯定取决于前面的序列的个数,在其末尾加个s[i],所以遍历从j到i的字符。
//例如1 2 7. 这个7的递增子序列是7,17,27,127. 而17正是在1的递增子序列的基础上加的1
//27,127正是在2的递增子序列的基础上加的1.
if(tmp[j] < tmp[i]) {
dp[i] += dp[j];
}
else if(tmp[j] == tmp[i]) {
dp[i] -= dp[j]; //因为s[j]和s[i]相同时,小于s【i】的,也小于s【j】,重复添加了。因为题目要求的本质同步递增,就是要去重的
//例如 : 1,2,7,3,7. 计算第二个7的dp【i】时,会包含1,2的个数,但是这个1,2的个数在第一个7中已经包含
//所以要减去。
}
}
}
int ans = 0;
//因为dp【i】记录的是以i结尾的本质不同递增子序列, 如果要求整个串的所有不同递增子序列个数,正是把这些子串的本质不同递增子序列相加总和。
for(int i = 0; i < dp.length; ++i) {
ans += dp[i];
}
System.out.println(ans);
}
}
本问题dp思路的理解:
https://blog.csdn.net/catrtees/article/details/113064117