674. 最长连续递增序列
原题链接:
https://leetcode.cn/problems/longest-continuous-increasing-subsequence/description/
完成情况:
解题思路:
这段代码是一个优化后的Java方法,用于解决不同的问题:寻找数组中最长连续递增子序列(Longest Continuous Increasing Subsequence,简称LCIS)的长度。与最长递增子序列(LIS)不同,LCIS要求子序列必须由连续的元素构成。
方法的名字是findLengthOfLCIS
,它遵循和lengthOfLIS
类似的模式,但是针对连续递增子序列作出了一个重要的改变。接下来是这个方法的解释:
public int findLengthOfLCIS(int[] nums) {
// ...
}
方法接受整型数组nums
作为输入,表示要分析的数列。
if (nums.length == 1){
return 1;
}
如果数组只含有一个元素,则最长连续递增子序列长度自然为1。
int [] dp = new int[nums.length];
Arrays.fill(dp,1);
int result = 1;
初始化一个跟输入数组同样长度的dp
数组,用来记录到当前位置为止的最长连续递增子序列的长度,并且为每个位置赋值初始长度为1(每个数字自身至少构成长度为1的序列)。result
变量初始化为1,它将用来记录并返回最长连续递增子序列的长度。
for (int i = 0; i < nums.length - 1; i++) {
// 只要记录出每一次的前后关系即可。
if (nums[i+1] > nums[i]){
dp[i+1] = dp[i] + 1;
}
result = result > dp[i+1] ? result : dp[i+1];
}
这里只有一个单层循环,它遍历数组nums
中的每个元素,除了最后一个,因为它没有后继元素可以比较。对于每一对相邻元素nums[i]
和nums[i+1]
,如果nums[i+1] > nums[i]
,那么nums[i+1]
就继续了一个递增序列,dp[i+1]
更新为dp[i] + 1
。
每一次遍历后都要更新result
,保证它保存最大的dp[i+1]
值。
return result;
最后,返回result
作为最长连续递增子序列的长度。
这个方法是用于连续递增子序列的计算,而不是任意递增子序列的情况,因此在找到不连续时不再更新dp[i+1]
。该算法的时间复杂度为O(n),其中n是输入数组nums
的长度,这要比最长递增子序列问题的O(n^2)时间复杂度要高效得多。
参考代码:
_674最长连续递增序列_贪心
package 代码随想录.动态规划;
import java.util.Arrays;
public class _674最长连续递增序列_贪心 {
/**
*
* @param nums
* @return
*/
public int findLengthOfLCIS(int[] nums) {
/*
public int lengthOfLIS(int[] nums) {
if (nums.length == 1){
return 1;
}
int [] dp = new int[nums.length];
int result = 0;
Arrays.fill(dp, 1);
for (int i = 1; i < nums.length; i++){
for (int j = 0;j<i;j++){
if (nums[i] > nums[j]){
dp[i] = Math.max(dp[i],dp[j]+1);
}
result = Math.max(result,dp[i]);
}
}
return result;
}
*/
//这次要求连续的情况了,就不能再使用二重for循环,去进行挨个的遍历
if (nums.length == 1){
return 1;
}
int result = 1;
int count = 1;
for (int i = 0; i < nums.length - 1; i++){
if (nums[i+1] > nums[i]){ //连续记录
count++;
}else { //不连续,count从头开始
count = 1;
}
if (count > result){
result = count;
}
}
return result;
}
}
_674最长连续递增序列_dp
package 代码随想录.动态规划;
import java.util.Arrays;
public class _674最长连续递增序列_dp {
/**
* 这次要求是连续的子系列了,其他的要求变量并没有改变
* @param nums
* @return
*/
public int findLengthOfLCIS(int[] nums) {
/*
public int lengthOfLIS(int[] nums) {
if (nums.length == 1){
return 1;
}
int [] dp = new int[nums.length];
int result = 0;
Arrays.fill(dp, 1);
for (int i = 1; i < nums.length; i++){
for (int j = 0;j<i;j++){
if (nums[i] > nums[j]){
dp[i] = Math.max(dp[i],dp[j]+1);
}
result = Math.max(result,dp[i]);
}
}
return result;
}
*/
//这次要求连续的情况了,就不能再使用二重for循环,去进行挨个的遍历
if (nums.length == 1){
return 1;
}
int [] dp = new int[nums.length];
Arrays.fill(dp,1);
int result = 1;
for (int i = 0;i<nums.length - 1;i++){
//只要记录出每一次的前后关系即可。
if (nums[i+1] > nums[i]){
dp[i+1] = dp[i] + 1;
}
result = result > dp[i+1] ? result : dp[i+1];
}
return result;
}
}