Leetcode 300. Longest Increasing Subsequence
题目链接: Count of Smaller Numbers After Self
难度:Medium
题目大意:
给出一个数组,求最长递增子序列的长度
思路:
参考leetcode官方题解,有动态规划和贪心+二分两种思路。
代码
动态规划
class Solution {
public int lengthOfLIS(int[] nums) {
int n=nums.length;
int[] dp=new int[n];
//dp[i]表示以nums[i]结尾的最长递增子序列的长度
for(int i=0;i<n;i++){
dp[i]=1;//每个单独的元素构成的子序列长度为1
}
int res=dp[0];
for(int i=1;i<n;i++){
for(int j=0;j<i;j++){
if(nums[i]>nums[j]){
dp[i]=Math.max(dp[j]+1,dp[i]);
}
}
res=Math.max(res,dp[i]);
}
return res;
}
}
贪心+二分
class Solution {
//参考https://leetcode-cn.com/problems/longest-increasing-subsequence/solution/zui-chang-shang-sheng-zi-xu-lie-by-leetcode-soluti/
public int lengthOfLIS(int[] nums) {
int n=nums.length;
int[] d=new int[n+1];
//d[i]表示长度为i的最长递增子序列的最后一个元素的最小值
int len=1;//最长递增子序列的长度
d[1]=nums[0];
for(int i=1;i<n;i++){
if(nums[i]>d[len]){
len++;
d[len]=nums[i];
}
else{
int l=0,r=len;
while(l<r){
//寻找比nums[i]小的元素的最大下标
int mid=l+(r-l+1)/2;
if(d[mid]>=nums[i]){
r=mid-1;
}
else{
l=mid;
}
}
d[l+1]=nums[i];
}
}
return len;
}
}