hdu1080 Human Gene Functions

http://acm.hdu.edu.cn/showproblem.php?pid=1080

题目大意:基因工程,给你两段基因序列,给定任意两个字符间的相似度,可以根据需要插入减号(-)与字符匹配,求这两段基因序列的最大相似度。

算法分析:一道dp题,类似于求两个字符串的编辑距离,主要找到状态转移方程:f[i][j] = Max(f[i][j - 1] + Match('-', s2[j]), f[i - 1][j] + Match('-', s1[i]), f[i - 1][j - 1] + Match(s1[i], s2[j]));

 

代码
   
     
/* dp题
状态转移方程:f[i][j] = Max(f[i][j - 1] + Match('-', s2[j]), f[i - 1][j] + Match('-', s1[i]), f[i - 1][j - 1] + Match(s1[i], s2[j]));
f[i][j]表示第一个字符串的前i个字符和第二个字符串的前j个字符的最大相似度
Match(a, b) 表示字符a与字符b的相似度,程序中预处理,存入数组mat[][]中
*/

#include
< stdio.h >
#define NN 102

int Max( int a, int b)
{
return a > b ? a : b;
}
int main()
{
int T, i, j, len1, len2;
char s1[NN], s2[NN];
int f[NN][NN], mat[NN][NN];
mat[
' A ' ][ ' A ' ] = mat[ ' C ' ][ ' C ' ] = mat[ ' G ' ][ ' G ' ] = mat[ ' T ' ][ ' T ' ] = 5 ;
mat[
' A ' ][ ' C ' ] = mat[ ' C ' ][ ' A ' ] = mat[ ' A ' ][ ' T ' ] = mat[ ' T ' ][ ' A ' ] = mat[ ' - ' ][ ' T ' ] = - 1 ;
mat[
' A ' ][ ' G ' ] = mat[ ' G ' ][ ' A ' ] = mat[ ' C ' ][ ' T ' ] = mat[ ' T ' ][ ' C ' ] = mat[ ' G ' ][ ' T ' ] = mat[ ' T ' ][ ' G ' ] = mat[ ' - ' ][ ' G ' ] = - 2 ;
mat[
' - ' ][ ' A ' ] = mat[ ' C ' ][ ' G ' ] = mat[ ' G ' ][ ' C ' ] = - 3 ;
mat[
' - ' ][ ' C ' ] = - 4 ;

scanf(
" %d " , & T);
while (T -- ){
scanf(
" %d%s%d%s " , & len1, s1, & len2, s2);
f[
0 ][ 0 ] = 0 ;
for (i = 1 ; i <= len1; i ++ )
f[i][
0 ] = f[i - 1 ][ 0 ] + mat[ ' - ' ][s1[i - 1 ]];
for (j = 1 ; j <= len2; j ++ )
f[
0 ][j] = f[ 0 ][j - 1 ] + mat[ ' - ' ][s2[j - 1 ]];
for (i = 1 ; i <= len1; i ++ ){
for (j = 1 ; j <= len2; j ++ ){
f[i][j]
= Max(f[i][j - 1 ] + mat[ ' - ' ][s2[j - 1 ]], Max(f[i - 1 ][j] + mat[ ' - ' ][s1[i - 1 ]], f[i - 1 ][j - 1 ] + mat[s1[i - 1 ]][s2[j - 1 ]]));
}
}

printf(
" %d\n " , f[len1][len2]);
}
return 0 ;
}

 

你可能感兴趣的:(functions)