DNA
Time Limit:5000MS Memory Limit:65536K
Total Submit:65 Accepted:5
Description
DNA能够表达数以百万计的基因密码,所用的仅仅是4种分子。我们分别用A、G、T和C表示这4种分子。一条基因就是DNA链上的一个由这4种分子组成的片段。人体按照一条基因上的分子序列可以合成出一种蛋白质。一条基因片段对应着一种蛋白质。
现在给定每种基因能合成出来的蛋白质的分数。但是,在蛋白质合成时,同一条DNA链可以用不同的方式解释出不同的基因片段。比如说,一条DNA链AATGCGG,可以解释出AATG 和 GG 这两个基因片段,也可以解释出AT 和 GCCG这两个基因片段。在同一种解释中,不得出现重叠的片段。你的任务是,仔细安排一条DNA链上的基因,让它能合成出来的蛋白质的分数总和最大。
Input
输入多个测试用例。每个测试用例的第一行是一个整数N(1 < N ≤ 100,000);接下来有N行,每行包括一个长度不超过10的表示基因片段的串S和一个整数C(按照基因片段S合成的蛋白质的分数);每个测试用例的最后一行是长度不超过1000的串(一条DNA链)。
Output
按照输出样例的格式输出每个测试用例的DNA链能合成的蛋白质的分数总和的最大值。
Sample Input
4
AATG 3
AT 2
GCGG 3
GG 2
AATGCGG
3
A 1
C 1
G 1
T
Sample Output
Case 1: 5
Case 2: 0
树形DP。。 DP+字典树。
状态转移方程很容易得出 那就是
DP[i]=max(dp[i-1],dp[i-k]+val,dp[i])( k就是子串的长度)
但是直接模拟应该会超时,所以要用字典树存储。
我是把每个字符串逆序存储的。。方便我这个转移方程。
下面是AC代码:
#include<iostream>
using namespace std;
#define N 100009
char input[1024],buff[1024];
int dp[1009];
int max(int a,int b){ return a>b?a:b;}
struct t_node
{
bool f;
int len,val;
int next[26];
void init(){ f=0; memset(next,-1,sizeof(next)); }
}trie[N*3];
int p;
void root ()
{ trie[p=0].init(); }
void insert(char *a,int val)
{
int index=0;
int len=strlen(a);
int cur,i;
for(i=len-1;i>=0;i--)
{
cur=a[i]-'A';
if(trie[index].next[cur]==-1)
{
trie[++p].init();
trie[index].next[cur]=p;
}
index=trie[index].next[cur];
}
trie[index].f=1;
trie[index].len=len;
trie[index].val=val;
}
int find(char *a,int k)
{
int index=0,i,cur;
int len=strlen(a);
for(i=len-1;i>=0;i--)
{
cur=a[i]-'A';
if(trie[index].next[cur]==-1)
return 0;
index=trie[index].next[cur];
if(trie[index].f==1)
{
dp[k+1]=max(dp[k+1],dp[k+1-trie[index].len]+trie[index].val);
}
}
return 0;
}
int main()
{
int n,i,k=0;
int len,val;
while(scanf("%d",&n)!=EOF)
{
root();
for(i=0;i<n;i++)
{
scanf("%s%d",buff,&val);
insert(buff,val);
}
scanf("%s",input);
len=strlen(input);
memset(dp,0,sizeof(dp));
for(i=0;i<len;i++)
{
dp[i+1]=dp[i];
strncpy(buff,input,i+1);
buff[i+1]='\0';
// printf("%s\n",buff);
find(buff,i);
// printf("%d\n",dp[i]);
}
printf("Case %d: ",++k);
printf("%d\n",dp[len]);
}
return 0;
}