zoukankan      html  css  js  c++  java
  • 最长非降子序列

    定义:一个包含n个数的序列a0, a1, ... , an-1,求序列的最长非降(>=)子序列及其长度。

    如:序列5, 3, 4, 9, 6, 8,此最大非降子序列长度为4,子序列为3,4,6,8.(子序列也可能不唯一)

    运用动态规划,可以构造时间复杂度为O(n2)的算法。

    算法基本思路:

    1.打表,获取最长非降子序列的长度;

    要构造最长非降子序列,可知此序列一定是以序列中某个数作为结尾(好像是废话,但就是那样)。

    因此,构造表ml[0...n-1],ml[i] 表示前 i 个数以a[i] 为结尾的最长非降子序列的长度。

    枚举 j (0 <= j < i),若a[j] <= a[i],则a[i]可在以a[j]为结尾的非降子序列后添加,此序列长度为ml[j] + 1.

    因此ml[i] = max(ml[j] + 1) (0 <= j < i) .

    构造出表ml后,遍历ml表,获取最大值。

    2.获取最长非降子序列的一个解。

    这个相当简单。只需要在构造表ml的过程中,添加表pre[0...n-1],pre[i] 保存当前a[i]为结尾的非降子序列的前一个元素的编号。

    在获得最长非降子序列的长度后,不断查找表pre即可找到整个序列。(pre 初始化为-1,表示序列的头)

    public class LIS{
    
        public static String getMaxLen(int[] a){
            //return the length of longest increasing subsequence and the subsequence
            int[] ml = new int[a.length];
            int[] pre = new int[a.length];
            //build length table
            for(int i = 0; i < ml.length; i ++){
                ml[i] = 1;
                pre[i] = -1;
                for(int j = 0; j < i; j ++){
                    if(a[j] <= a[i] && ml[j] + 1 > ml[i]){
                        ml[i] = ml[j] + 1;
                        pre[i] = j;
                    }
                }
            }
            //find max length
            int k = 0;
            for(int i = 1; i < ml.length; i ++){
                if(ml[k] < ml[i]){
                    k = i;
                }
            }
            String result = Integer.toString(ml[k]);
            String temp = "";
            //get subsequence
            while(k != -1){
                temp = Integer.toString(a[k]) + " " + temp;
                k = pre[k];
            }
            result += "/" + temp;
            return result;
        }
    
        public static void main(String[] args) {
            int[] a = {5, 3, 4, 9, 6, 8};
            String[] result = getMaxLen(a).split("/");
            System.out.println(result[0]);
            System.out.println(result[1]);
        }
        
    }
    Java
  • 相关阅读:
    Union用法及说明:
    SQL用了Union后的排序问题
    10条PHP编程习惯助你找工作
    PHP性能分析工具xhprof的安装使用与注意事项
    11款数据分析工具(附体验网址)
    Linux下的库操作工具-nm、ar、ldd、ldconfig和ld.so
    ldd显示可执行模块的dependenc
    计算机图形学,三维框架设计
    dnat,snat
    百度识图API
  • 原文地址:https://www.cnblogs.com/7hat/p/3446049.html
Copyright © 2011-2022 走看看