zoukankan      html  css  js  c++  java
  • poj3356 AGTC 解题心得

    原题:

    Description

    Let x and y be two strings over some finite alphabet A. We would like to transform x into y allowing only operations given below:

    • Deletion: a letter in x is missing in y at a corresponding position.
    • Insertion: a letter in y is missing in x at a corresponding position.
    • Change: letters at corresponding positions are distinct

    Certainly, we would like to minimize the number of all possible operations.

    Illustration
    A G T A A G T * A G G C 
    | | | | | | |
    A G T * C * T G A C G C
    Deletion: * in the bottom line 
    Insertion: * in the top line 
    Change: when the letters at the top and bottom are distinct

    This tells us that to transform x = AGTCTGACGC into y = AGTAAGTAGGC we would be required to perform 5 operations (2 changes, 2 deletions and 1 insertion). If we want to minimize the number operations, we should do it like

    A  G  T  A  A  G  T  A  G  G  C 
    | | | | | | |
    A G T C T G * A C G C

    and 4 moves would be required (3 changes and 1 deletion).

    In this problem we would always consider strings x and y to be fixed, such that the number of letters in x is m and the number of letters in y is n where n ≥ m.

    Assign 1 as the cost of an operation performed. Otherwise, assign 0 if there is no operation performed.

    Write a program that would minimize the number of possible operations to transform any string x into a string y.

    Input

    The input consists of the strings x and y prefixed by their respective lengths, which are within 1000.

    Output

    An integer representing the minimum number of possible operations to transform any string x into a string y.

    Sample Input

    10 AGTCTGACGC
    11 AGTAAGTAGGC

    Sample Output

    4


    分析:
    dp[i][j]表示第一个字符串的前i个字符要和第二个字符串的前j个字符匹配需要的最少操作次数  
    初始化dp[i][0]=i,若第二个字符串为0,只好把第一个字符串全删掉,所以dp[i][0]=i  同理,dp[0][j]=j  
    状态转移方程:若s1[i-1]==s2[j-1],则不需要操作,那么dp[i][j]=dp[i-1][j-1] 
     
    否则,我们可能有三步操作,删除,插入,变换,所以dp[i][j]=min(dp[i-1][j]+1,dp[i][j-1]+1,dp[i-1][j-1]+1)  
    把删除和插入看作是一个操作,自然dp[i-1][j-1]+1对应的是变换了。  

    代码:
    #include<iostream>
    #include<cstdlib>
    #include<stdio.h>
    #include<memory.h>
    using namespace std;
    int dp[1010][1010];
    char s1[1010];
    char s2[1010];
    int main()
    {
        int l1,l2;
        while(scanf("%d%s%d%s",&l1,s1,&l2,s2)!=EOF)
        {
            for(int i=0;i<=l1;i++)
            for(int j=0;j<=l2;j++)
            dp[i][j]=0;
            for(int i=1;i<=l1;i++) dp[i][0]=i;
            for(int j=1;j<=l2;j++) dp[0][j]=j;
            for(int i=1;i<=l1;i++)
            for(int j=1;j<=l2;j++)
            {
                if(s1[i-1]==s2[j-1]) dp[i][j]=dp[i-1][j-1];
                else dp[i][j]=min(dp[i-1][j]+1,dp[i][j-1]+1),dp[i][j]=min(dp[i][j],dp[i-1][j-1]+1);
            }
            cout<<dp[l1][l2]<<endl;
        }
    }
    
    
    
     
  • 相关阅读:
    Eclipse 远程调试
    大数据处理方法bloom filter
    sicily 1259 Sum of Consecutive Primes
    sicily 1240. Faulty Odometer
    sicily 1152 简单马周游 深度优先搜索及回溯算法
    sicily 1050 深度优先搜索解题
    sicily 1024 邻接矩阵与深度优先搜索解题
    sicily 1156 二叉树的遍历 前序遍历,递归,集合操作
    sicily 1443 队列基本操作
    sicily 1006 team rankings 枚举解题
  • 原文地址:https://www.cnblogs.com/shawn-ji/p/4732786.html
Copyright © 2011-2022 走看看