zoukankan      html  css  js  c++  java
  • 动态规划算法实现部分——求公共最长子序列以及构造回文需要删除的最小字符个数

    上学期的期末考为了应付考试,只是把每种算法都理解了一遍,但是并没有具体的代码实现。现在开始抽空慢慢实现这些算法。

    代码实现:

    import java.util.Scanner;
    
    public class Main2
    {
        public static void main(String[] args){
            //从键盘输入第一个字符串
            Scanner in=new Scanner(System.in);
            String string1=in.nextLine();
            //从键盘输入第二个字符串
            String string2=in.nextLine();
            in.close(); //关闭输入
            
            char[] chars1=string1.toCharArray();
            char[] chars2=string2.toCharArray();
            int length1=string1.length();
            int length2=string2.length();
            
            /*这里要加1,因为要构造的那个二维数组是行和列都是从0比到6的
              会比原字符串的长度多1
            */
            int dp[][]=new int[length1+1][length2+1];
            /*后面为了对齐方向箭头打印位置初始从1开始打印,所以这里长度加2,避免数组溢出*/
            char b[][]=new char[length1+2][length2+1];
                
            /*构造第一排和第一列的所有的0*/
            for(int i=0; i<=length1;i++){
                dp[i][0]=0;
            }
            for(int j=1;j<=length2;j++){
                dp[0][j]=0;
            }
            
            //自底向上计算
            for(int i=1;i<=length1;i++){
                for(int j=1;j<=length2;j++){
                    if(chars1[i-1]==chars2[j-1]){
                        dp[i][j]=dp[i-1][j-1]+1;
                        b[i][j]='↖';
                    }else if(dp[i][j-1]>dp[i-1][j]){
                        dp[i][j]=dp[i][j-1];
                        b[i][j]='←';
                    }else{
                        dp[i][j]=dp[i-1][j];
                        b[i][j]='↑';
                    }
                }
            }
            
            /*输出*/
            for(int i=0;i<=length1;i++){
                for(int j=0;j<=length2;j++){
                    System.out.print(dp[i][j]+"  ");
                }
                System.out.println();
                for(int j=0;j<=length2;j++){
                    System.out.print(b[i+1][j]+" ");//为了对齐方向箭头,从第二行开始逐行打印
                }
                System.out.println();
            }
        }
    }

     结果:

    这里有个算法的衍生,就是求构造回文需要删除的最小字符个数。其实只需要将一个字符串和它的逆序字符串求公共最长子串就可以了。

    import java.util.Scanner;
    
    public class Main
    {
        public static void main(String[] args){
            Scanner in=new Scanner(System.in);
            while(in.hasNext()){ //循环输入
                String string=in.nextLine();
                char[] chars=string.toCharArray();
                int length=string.length();
                int dp[][]=new int[length+1][length+1];
                
                /*构造第一排和第一列的所有的0*/
                for(int i=0; i<length+1;i++){
                    dp[i][0]=0;
                    dp[0][i]=0;
                }
                //自底向上计算
                for(int i=1;i<=length;i++){
                    for(int j=1;j<=length;j++){
                        if(chars[i-1]==chars[length-j]){
                            dp[i][j]=dp[i-1][j-1]+1;
                        }else if(dp[i][j-1]>dp[i-1][j]){
                            dp[i][j]=dp[i][j-1];
                        }else{
                            dp[i][j]=dp[i-1][j];
                        }
                    }
                }
                //输出构造回文需要删除的最少字符的个数
                System.out.println(length - dp[length][length]);
            }
        }
    }
  • 相关阅读:
    zend studio 的vim插件
    [转]mysql性能优化慢查询分析、优化索引和配置
    mysql日期函数整理
    系统进行多语言支持转换
    table xxxx is full 报警问题处理
    坚持的力量
    $_SERVER内容的意义
    smarty 注册函数使用初体验
    Mysql输入错误时取消输入
    js:
  • 原文地址:https://www.cnblogs.com/f91og/p/6477207.html
Copyright © 2011-2022 走看看