1. 最長増加サブシーケンス
与えられた整数 nums の配列で、その中で最も長く厳密に増加するサブシーケンスの長さを見つけます。
サブシーケンスは、残りの要素の順序を変更せずに要素が削除された (または削除されなかった) 配列から派生したシーケンスです。たとえば、[3,6,2,7] は配列 [0,3,1,6,2,2,7] のサブシーケンスです。
一連の考え
1.dp[i]: nums[i] で終わる最長の増加サブシーケンスの長さを示します
2. 再帰式: dp[i] = max(dp[j] + 1,dp[i]) j は 0 から i まで移動します-1
3. 初期化: dp[i] = 1 各 i について、対応する dp[i] の開始サイズは少なくとも 1 です 4.
走査順序: 前から後ろへ走査
最終結果: 各 nums[i] まで走査最後に最も長く増加するサブシーケンスの長さ、最大値を見つける
実装コード
class Solution {
public:
int lengthOfLIS(vector<int>& nums) {
if(nums.size() <= 1) return nums.size();
vector<int> dp(nums.size(),1);
int result = 0;
for(int i = 1; i < nums.size(); i++) {
for(int j = 0; j < i; j++) {
if(nums[i] > nums[j]) dp[i] = max(dp[i], dp[j] + 1);
}
if(dp[i] > result) result = dp[i];
}
return result;
}
};
2. 最長の連続増加シーケンス
整数のソートされていない配列を指定して、連続的に増加する最長のサブシーケンスを見つけ、そのシーケンスの長さを返します。
一連の考え
1. dp[i]: i で終わる最長の増加サブシーケンスの長さを示します
2. 再帰式: if(nums[[i] > nums[i - 1]) dp[i] = dp[i - 1] + 1 (連続)
3. 初期化: dp[i] = 1
4. 走査順序: 前から後ろへ走査
実装コード
class Solution {
public:
int findLengthOfLCIS(vector<int>& nums) {
if(nums.size() <= 1) return nums.size();
vector<int> dp(nums.size(), 1);
int result = 0;
for(int i = 1; i < nums.size(); i++) {
if(nums[i] > nums[i - 1]) dp[i] = dp[i - 1] + 1;
if(dp[i] > result) result = dp[i];
}
return result;
}
};
3. 最長繰り返し部分配列
2 つの整数配列 A と B を指定して、両方の配列に共通する最長の部分配列の長さを返します。
サブ配列は、サブ配列の連続したシーケンスです
一連の考え
1.dp[i][j]: nums1 は i-1 で終わり、nums2 は j-1 で終わり、最も長く繰り返される部分配列の長さは dp[i][j] です。
dp[i][j] が添字 i で終わる A と添字 j で終わる B として定義されている場合、nums1[i] が nums2[0] と同じ場合、最初の行と最初の列が初期化されます。 、対応する dp[i][0] は最初は 1 になります。これは、この時点で最も長く繰り返されるサブ配列が 1 であるためです。nums2[j] が nums1[0] と同じ場合、同じです。
2. 再帰式: if(nums[i- 1] == nums[j- 1]) dp[i][j] = dp[i - 1][j- 1] +1 3. 初期化: dp [
i ][0] = 0 dp[0][j] = 0 他の添字配列は 0 に初期化されます
4. 走査順序: nums1/nums2 を走査し、次に nums2/nums1 を走査します
最終結果: すべての 2 次元配列を走査し、最も長い配列を見つけます子配列の繰り返し
実装コード
class Solution {
public:
int findLength(vector<int>& nums1, vector<int>& nums2) {
vector<vector<int>> dp(nums1.size() + 1, vector<int>(nums2.size() + 1, 0));
int result = 0;
for(int i = 1; i <= nums1.size(); i++) {
for(int j = 1; j <= nums2.size(); j++) {
if(nums1[i - 1] == nums2[j - 1]) {
dp[i][j] = dp[i - 1][j - 1] + 1;
}
if(dp[i][j] > result) result = dp[i][j];
}
}
return result;
}
};