package dp;

 /**
* 最长上升子序列问题
*/
public class LongestIncreasingSubsequence
{
/**
* 原始dp
* @param arr
* @return
*/
public static int maxLength(int[] arr)
{
int[] len = new int[arr.length] ; //以i为结尾的最长上升子序列
int[] mark = new int[arr.length] ;//标记以i为结尾的最长上升子序列的上一个节点所在的上上子序列位置
len[0] = 1 ;
mark[0] = -1 ; int maxPos = 0 ;
for(int i=1 ; i<len.length ; i++)
{
len[i] = 1 ;
mark[i] = -1 ;
for(int j=i-1 ; j>=0 ; j--)
{
if(arr[j] < arr[i] && (len[j]+1) > len[i])
{
len[i] = len[j]+1 ;
mark[i] = j ;
} }
if(len[maxPos] < len[i])
maxPos = i ;
} int maxP = maxPos ;
while (maxP != -1)
{
System.out.println(arr[maxP]);
maxP = mark[maxP] ;
}
return len[maxPos] ;
} /**
* 使用二分加速的dp
* @param arr
* @return
*/
public static int maxLength2(int[] arr)
{
int[] len = new int[arr.length] ; //以i为结尾的最长上升子序列
int[] mark = new int[arr.length] ;//标记以i为结尾的最长上升子序列的上一个节点所在的上上子序列位置
int[] m = new int[arr.length+1] ;//标记长度为x的子序列的最小值在arr中的位置 int mLength = 1 ;
len[0] = 1 ;
mark[0] = -1 ;
m[1] = 0 ; int maxPos = 0 ;
for(int i=1 ; i<len.length ; i++)
{
len[i] = 1 ;
mark[i] = -1 ; int pos = binarySearch(arr , m , mLength , arr[i]) ; if(pos != -1)
{
len[i] = len[pos]+1 ;
mark[i] = pos ;
} if(mLength < len[i])
{
m[len[i]] = i ;
mLength++ ;
}
else if(arr[m[len[i]]] > arr[i])
{
m[len[i]] = i ;
} if(len[maxPos] < len[i])
maxPos = i ;
} int maxP = maxPos ;
while (maxP != -1)
{
System.out.println(arr[maxP]);
maxP = mark[maxP] ;
}
return len[maxPos] ;
} /**
* 寻找arr中比k小的最大数
* @param n 表示m的长度
* @param m 表示标记长度为x的子序列的最小值的位置的数组
* @return 该元素在arr中的位置(为标记函数而服务的)
*/
private static int binarySearch(int[] arr , int[] m , int n , int k) {
int lo = 1;
int hi = n; while ((hi-lo) > 1)
{
int mid = lo + (hi-lo)/2 ; if(arr[m[mid]] < k)
lo = mid ;
else
hi = mid ;
} if(arr[m[hi]] < k)
return m[hi] ;
else if(arr[m[lo]] < k)
return m[lo] ;
else
return -1 ;
} public static void main(String[] args) {
int[] arr = new int[]{
// 1,4,8,3,4,5
// 3,5,1,7,5,9,3,5
1, 7, 3, 5, 9, 4, 1
} ; System.out.println(maxLength2(arr));
}
}

//http://blog.csdn.net/code_pang/article/details/8757380

//http://blog.csdn.net/chenwenshi/article/details/6027086

longestIncreasingSequence最长上升子序列问题的更多相关文章

  1. 用python实现最长公共子序列算法(找到所有最长公共子串)

    软件安全的一个小实验,正好复习一下LCS的写法. 实现LCS的算法和算法导论上的方式基本一致,都是先建好两个表,一个存储在(i,j)处当前最长公共子序列长度,另一个存储在(i,j)处的回溯方向. 相对 ...

  2. 动态规划之最长公共子序列(LCS)

    转自:http://segmentfault.com/blog/exploring/ LCS 问题描述 定义: 一个数列 S,如果分别是两个或多个已知数列的子序列,且是所有符合此条件序列中最长的,则 ...

  3. [Data Structure] LCSs——最长公共子序列和最长公共子串

    1. 什么是 LCSs? 什么是 LCSs? 好多博友看到这几个字母可能比较困惑,因为这是我自己对两个常见问题的统称,它们分别为最长公共子序列问题(Longest-Common-Subsequence ...

  4. 动态规划求最长公共子序列(Longest Common Subsequence, LCS)

    1. 问题描述 子串应该比较好理解,至于什么是子序列,这里给出一个例子:有两个母串 cnblogs belong 比如序列bo, bg, lg在母串cnblogs与belong中都出现过并且出现顺序与 ...

  5. LintCode 77: 最长公共子序列

    public class Solution { /** * @param A, B: Two string. * @return: the length of the longest common s ...

  6. 最长下降子序列O(n^2)及O(n*log(n))解法

    求最长下降子序列和LIS基本思路是完全一样的,都是很经典的DP题目. 问题大都类似于 有一个序列 a1,a2,a3...ak..an,求其最长下降子序列(或者求其最长不下降子序列)的长度. 以最长下降 ...

  7. 删除部分字符使其变成回文串问题——最长公共子序列(LCS)问题

    先要搞明白:最长公共子串和最长公共子序列的区别.    最长公共子串(Longest Common Substirng):连续 最长公共子序列(Longest Common Subsequence,L ...

  8. [BZOJ3173][Tjoi2013]最长上升子序列

    [BZOJ3173][Tjoi2013]最长上升子序列 试题描述 给定一个序列,初始为空.现在我们将1到N的数字插入到序列中,每次将一个数字插入到一个特定的位置.每插入一个数字,我们都想知道此时最长上 ...

  9. 3173: [Tjoi2013]最长上升子序列

    原题:http://www.lydsy.com/JudgeOnline/problem.php?id=3173 题解:促使我写这题的动力是,为什么百度遍地是Treap,黑人问号??? 这题可以用线段树 ...

随机推荐

  1. 【CCF】无线网络 搜索

    [思路] 多个起点同时四周扩展广搜,注意会爆int [AC] #include<iostream> #include<cstdio> #include<cstring&g ...

  2. C++ 错误解决 —— internal compiler error

    问题: g++ 编译时,报错: g++: internal compiler error: Killed (program cc1plus) 出错原因: 出错的原因是(虚拟机)运行内存不足,而大量te ...

  3. [暑假集训--数位dp]UESTC250 windy数

    windy定义了一种windy数. 不含前导零且相邻两个数字之差至少为22 的正整数被称为windy数. windy想知道,在AA 和BB 之间,包括AA 和BB ,总共有多少个windy数? Inp ...

  4. ideaaaaaaaaa

    数据库proxy:可以用作自动化数据逆向SQL test4j/jtester:

  5. 前端开发 CSS中你所不知道的伪类与伪元素的区别--摘抄

    做过前端开发的人都熟悉伪类与伪元素,而真正能够彻底了解这二者的区别的人并不多.伪类与伪元素确实很容易混淆. 伪元素主要是用来创建一些不存在原有dom结构树种的元素,例如:用::before和::aft ...

  6. linux shmget shmctl

    shmgetint shmget(key_t key, size_t size, int flag);key: 标识符的规则size:共享存储段的字节数flag:读写的权限返回值:成功返回共享存储的i ...

  7. dedecms--数据库

    最近在用dedecms做项目,dedecms里面有数据库操作类,其实这个在实际项目中用起来还是很方便的. 1:引入common.inc.php文件 require_once (dirname(__FI ...

  8. Python初见

    参考资料:http://wenku.baidu.com/link?url=_akpT-G5Tvf7ECyszSipOAhHXzjlpYu-RWPcRTYp_tecPOollPGUxXG4MH69MLN ...

  9. E. Sergey and Subway

    比赛时候写复杂了…… 我写的是 计算每个节点树内所有点到某个点的距离和. #include <bits/stdc++.h> using namespace std; typedef lon ...

  10. HTTP/1.1标准请求方法和状态码

    HTTP/1.1标准自从1999年制定以来至今仍然是一个应用广泛并且通行的标准 相关文档 RFC2616:Hypertext Transfer Protocol -- HTTP/1.1 在RFC658 ...