Leetcode 300 Longest Increasing Subsequence

来源:互联网 发布:劳动收入份额数据 编辑:程序博客网 时间:2024/05/16 00:17

Leetcode 300 Longest Increasing Subsequence

Description

Given an unsorted array of integers, find the length of longest increasing subsequence.
For example,Given [10, 9, 2, 5, 3, 7, 101, 18],The longest increasing subsequence is [2, 3, 7, 101], therefore the length is 4. Note that there may be more than one LIS combination, it is only necessary for you to return the length.
Your algorithm should run in O(n2) complexity.

题解

题目意思很简单,找出给出序列的最长增长子序列,直接用动态规划的方法,dp[i]表示第i个元素前面有多少个比它小的数字,状态转移方程是if nums[i] > nums[i - 1] dp[i] = dp[i - 1] + 1,代码如下:

class Solution {public:    int lengthOfLIS(vector<int>& nums) {        vector<int> dp(nums.size(), 0);        int max = -1;        for (int i = 0; i < nums.size(); i++) {            for (int j = i + 1; j < nums.size(); j++) {                if (nums[j] > nums[i] && dp[j] <= dp[i])                    dp[j] = dp[i] + 1;            }            if (max < dp[i])                max = dp[i];        }        for (int i = 0; i < nums.size(); i++)            cout << dp[i] << endl;        return max + 1;    } };

上面的解法时间复杂度是O(n2),如果用二分的方法实现的话可以让复杂度下降为O(nlogn),代码如下:

class Solution {public:    int lengthOfLIS(vector<int>& nums) {        vector<int> res;        for(int i=0; i<nums.size(); i++) {            // low_bound会返回以元素nums[i]为分界点的左闭右开的区间的最右元素的指针,即第一个不大于nums[i]的元素            auto it = std::lower_bound(res.begin(), res.end(), nums[i]);            if(it==res.end()) res.push_back(nums[i]);            else *it = nums[i];        }        return res.size();    }};