时间限制:2000ms
单点时限:1000ms
内存限制:256MB
描述
给定字符串,求它的回文子序列个数。回文子序列反转字符顺序后仍然与原序列相同。例如字符串aba中,回文子序列为”a”, “a”, “aa”, “b”, “aba”,共5个。内容相同位置不同的子序列算不同的子序列。
输入
第一行一个整数T,表示数据组数。之后是T组数据,每组数据为一行字符串。
输出
对于每组数据输出一行,格式为”Case #X: Y”,X代表数据编号(从1开始),Y为答案。答案对100007取模。
数据范围
1 ≤ T ≤ 30
小数据
字符串长度 ≤ 25
大数据
字符串长度 ≤ 1000
样例输入
5
aba
abcbaddabcba
12111112351121
ccccccc
fdadfa
样例输出
Case #1: 5
Case #2: 277
Case #3: 1333
Case #4: 127
Case #5: 17
中心思想是dp[i+1][j+1]=dp[i+1][j]+dp[i][j+1]-dp[i][j];
import java.util.Scanner;
public class Palindrome_Sub_Sequence {
public static void main(String[] args) {
int dp[][] = new int[1005][1005];
final int MOD = 100007;
int count=1;
int q=1;
Scanner in = new Scanner(System.in);
int n = in.nextInt();
while (n--!= 0) {
if (q==1) {
in.nextLine();
q++;
}
String A = in.nextLine();
char a[] = A.toCharArray();
int m = A.length();
int i,j;
//System.out.println(n);
for ( i = 0; i < m; i++) {
dp[i][i] = 1;
}
for ( i = 1; i < m; i++) {
for ( j = i - 1; j >= 0; j--) {
dp[j][i] = (dp[j + 1][i] + dp[j][i - 1] - dp[j + 1][i - 1] + MOD)
% MOD;
if ((a[i] - '0') == (a[j] - '0'))
dp[j][i] = (dp[j][i] + dp[j + 1][i - 1] + 1 + MOD)
% MOD;
}
}
//System.out.println("Case #%d: "+dp[0][n-1]);
System.out.printf("Case #%d: %d\n", count++, dp[0][m-1]);
}
in.close();
}
}