The longest increasing subsequence two approaches

The longest increasing subsequence two approaches

Here to give a example, you can complete understanding to do it. HRBUST-1835

Complexity \ (O (N ^ 2) \) approach

Dynamic programming approach

Has a length N of the array {a0, a1, a2, a3, ..., an-1}, we assume that the array is incremented to the longest sequence aj ending subsequence length dp [j], then dp [j ] = max (dp [i] +1, i <j and a [i] <a [j]). We need to traverse all positions before i j, find the greatest value of this.

For more details see the other code.

#include<cstdio>
#include<cmath>
#include<cstring>
#include<algorithm>

using namespace std;
const int N=1e3;
int a[N];
int dp[N];
int main()
{
    int n;
    while(scanf("%d", &n)!=EOF)
    {
        for(int i=0; i<n; i++)
        {
            scanf("%d", &a[i]);
            dp[i]=1; //每个需要初始化为1,因为每一个都可以自己成为一个最短的子序列
        }
        int ans=1;//答案最小是1
        for(int i=1; i<n; i++)
        {
            for(int j=0; j<i; j++)
            {
                if(a[j]<a[i] && dp[j]+1 > dp[i]) //这里需要满足两个条件,前面的数值小于a[i],并且加上这个序列后能够使得dp[i]增加。
                {         
                    dp[i]=dp[j]+1;
                }
            }
            ans=max(ans, dp[i]);//这里求出dp中的最大值。
        }
        printf("%d\n", ans);
    }
    return 0;
 } 

Complexity \ (O (N * lgN) \) algorithm

For an increasing sequence of length n, we want this number as small as possible at the end of the sequence, because only then when we want to add a digital back, this figure can be relatively small.

Such a process is.

Suppose there is a sequence d [1..9] = {2,1, 5, 3, 6,4, 8, 9, 7}, it can be seen LIS length of 5. The following step by step, try to find it.
We define a sequence of B, and so i = 1 to 9 individually examine this sequence. In addition, we use a variable to record Len now up to count the number of

First, the D [1] in an orderly manner into B, so that B [1] = 2, a number that is a time when only 2, the minimum length of the end of the LIS is 2 to 1. Then Len = 1

Then, d [2] in an orderly manner into B, so that B [1] = 1, that is the minimum length of the end of the LIS 1 is 1, d [1] = 2 has been useless, it is readily appreciated it. Then Len = 1

Then, d [3] = 5, d [3]> B [1], so it is B [1 + 1] = B [2] = d [3] = 5, that is the minimum length of the end of the LIS 2 5, it is easy to understand it. This time B [1..2] = 1, 5, Len = 2

Again, d [4] = 3, it is just applied between 1,5, is placed at position 1 clearly inappropriate, because 1 is less than 3, the length of the end of the LIS 1 should be a minimum, it is easy to deduce the length 2 to the end of the LIS is minimum 3, 5 can thus eliminate this time B [1..2] = 1, 3, Len = 2

Continue, d [5] = 6, 3 behind it, because the B [2] = 3, 3 and 6 in the back, so can easily deduce B [3] = 6, time B [1..3] = 1, 3, 6, or easy to understand, right? Len = 3 oh.

Sixth, d [6] = 4, you see it between 3 and 6, so we can replace 6, to obtain B [3] = 4. B [1..3] = 1, 3, 4, Len continues equal to 3

7th, d [7] = 8, it is large, larger than 4, ah. Then B [4] = 8. Len turned into a 4

8th, d [8] = 9, to obtain B [5] = 9, ah. Len continues to increase, up to 5.

Finally a, d [9] = 7, in which B [. 3] = 4 and between B [4] = 8, so we know the latest B [4] = 7, B [1..5] = 1 , 3, 4, 7, 9, Len = 5.

So we know the length of the LIS is 5.

This last number of array B is stored in the corresponding end of the LIS minimum length, the length of the sequence is the same, the minimum value of the end.

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=107;
int a[maxn];
int main()
{
    int n;
    while(scanf("%d", &n)!=EOF)
    {
        for(int i=1; i<=n; i++)
        {
            scanf("%d", &a[i]);
        }
        int len=1, pos;
        for(int i=2; i<=n; i++)//这里我没有用两个数组,因为使用原来的数组也可以
        {
            pos=lower_bound(a+1, a+len+1, a[i])-a; //这里使用了lower_bound函数来进行查找第一个小于等于a[i]的数字
            if(pos>len)//如果位置大于了len长度的时候需要len++
                len++;
            a[pos]=a[i];
        }
        printf("%d\n", len);
    } 
    return 0;
 } 

Reference article

click here

Guess you like

Origin www.cnblogs.com/alking1001/p/11537203.html
Recommended