leetcoe 面試題 16.17. 42.連續數列最大和
題目
給定一個整數數組,找出總和最大的連續數列,並返回總和。
示例
輸入: [-2,1,-3,4,-1,2,1,-5,4]
輸出: 6
解釋: 連續子數組 [4,-1,2,1] 的和最大,爲 6。
代碼
class Solution {
public:
int maxSubArray(vector<int>& nums) {
if(nums.size() == 0) return 0;
vector<int> dp(nums.size());
dp[0] = nums[0];
int res = dp[0];
for(int i = 1; i < nums.size(); i++){
dp[i] = dp[i-1] > 0 ? (dp[i-1]+nums[i]) : nums[i];
res = max(res, dp[i]);
}
return res;
}
};
leetcode.1143. 最長公共子序列
題目
給定兩個字符串 text1 和 text2,返回這兩個字符串的最長公共子序列的長度。
一個字符串的 子序列 是指這樣一個新的字符串:它是由原字符串在不改變字符的相對順序的情況下刪除某些字符(也可以不刪除任何字符)後組成的新字符串。
例如,“ace” 是 “abcde” 的子序列,但 “aec” 不是 “abcde” 的子序列。兩個字符串的「公共子序列」是這兩個字符串所共同擁有的子序列。
若這兩個字符串沒有公共子序列,則返回 0
示例
輸入:text1 = "abcde", text2 = "ace"
輸出:3
解釋:最長公共子序列是 "ace",它的長度爲 3。
代碼
class Solution {
public:
int longestCommonSubsequence(string text1, string text2) {
int m = text1.size(), n = text2.size();
int dp[m+1][n+1];
memset(dp, 0, sizeof dp);
for(int i = 0; i <= m; i++) dp[i][0] = 0;
for(int i = 0; i <= n; i++) dp[0][i] = 0;
for(int i = 0; i < m; i++)
{
for(int j = 0; j < n; j++)
{
if(text1[i] == text2[j])
dp[i+1][j+1] = dp[i][j]+1;
else
dp[i+1][j+1] = max(dp[i][j+1],dp[i+1][j]);
}
}
return dp[m][n];
}
};
leetcode. 300最長上升子序列
題目
給定一個無序的整數數組,找到其中最長上升子序列的長度。
示例
輸入: [10,9,2,5,3,7,101,18]
輸出: 4
解釋: 最長的上升子序列是 [2,3,7,101],它的長度是 4。
代碼
class Solution {
public:
int lengthOfLIS(vector<int>& nums) {
int len = nums.size();
if(len == 0)
return 0;
int dp[len];
for(int i = 0; i < len; i++)
{
dp[i] = 1;
}
for(int i = 1; i < len; i++)
{
for(int j = 0; j < i; j++)
{
if(nums[i] > nums[j])
{
dp[i] = max(dp[i],dp[j]+1);
}
}
}
int maxLen = 0;
for(int i = 0; i < len; i++)
{
maxLen = max(maxLen,dp[i]);
}
return maxLen;
}
};
數組和湊數字
題目
一個數組都爲正數,可以離散選擇數組中的數字,判斷能夠湊成給定SUM值。
示例
輸入:[3,2,7,9],10
輸出:false
思路
先寫遞歸函數
bool process(int arr[], int i, int sum, int value){
if(i == arr.size()){
return value == sum;
}else
return process(arr, i+1, sum, value) || process(arr, i+1, sum+arr[i], value);
}
對於數組的數字,選擇要還是不要。
dp設計爲一個二維數組,行範圍爲i 的範圍,表示每一個數組位置。列範圍爲數組和的範圍, 如例子中爲 0- 10,因爲都是正數,多了沒用。
0 1 2 · · · · · · · · · · · · · 10
1
·
·
·
·
N
這樣一個二維數組,初始化最後一行(表示i==len)dp[n][sum]一定是true, 其他都是false.
依賴關係, (i, sum)依賴於(i+1, sum)和(i+1, sum + arr[i])
得到遞推關係式
dp[i][j] = dp[i+1][j] || dp[i+1][j + arr[i]]
從最後一行得到倒數第二行,以此類推,一直往上推,得到dp[0][0] 判斷是true還是
false,就可以得到。
代碼
leetcode. 三步問題
題目
三步問題。有個小孩正在上樓梯,樓梯有n階臺階,小孩一次可以上1階、2階或3階。實現一種方法,計算小孩有多少種上樓梯的方式。結果可能很大,你需要對結果模1000000007。
示例
輸入:n = 3
輸出:4
輸入:n = 1000000
輸出:746580045
輸入:n = 78
輸出:361781289
提示:n的範圍 [1, 1000000]
模的處理做不好。
代碼
class Solution {
public:
int waysToStep(int n) {
if(n <= 1) return 1;
if(n == 2) return 2;
if(n == 3) return 4;
vector<long> dp(n, 0);
dp[0] = 1, dp[1] = 2, dp[2] = 4;
for(int i = 3; i < n; i++){
dp[i] = ((dp[i-1] + dp[i-2])%1000000007 + dp[i-3])%1000000007;
}
return (int)dp[n-1]%1000000007;
}
};