2020-12-26 Daily-Challenge
Today is Saturday, I gonna review the tasks I've done this week, and finish today's leetcode's November LeetCoding Challenge with cpp
.
LeetCode Review
Smallest Range I
nothing to say
class Solution {
public:
int smallestRangeI(vector<int>& A, int K) {
int mmin = INT_MAX, mmax = INT_MIN;
for(auto i : A) {
mmin = min(mmin, i);
mmax = max(mmax, i);
}
return max(mmax-mmin-2*K, 0);
}
};
Smallest Range II
class Solution {
public:
int smallestRangeII(vector<int>& A, int K) {
if(A.size() < 2) return 0;
sort(A.begin(), A.end());
int answer = A.back() - A.front();
for(int i = 1; i < A.size(); ++i) {
int high = max(A.back()-K, A[i-1]+K);
int low = min(A.front()+K, A[i]-K);
answer = min(answer, high-low);
}
return answer;
}
};
Shopping Offers
don't want to review it.
Next Greater Element III
don't want to write a next_permutation
Make Two Arrays Equal by Reversing Sub-arrays
too easy to review
Path Sum
too easy to review
Swap Nodes in Pairs
too easy to review
Diagonal Traverse
too easy to review
Balanced Binary Tree
class Solution {
pair<int, bool> helper(TreeNode *root) {
if(!root) return make_pair(0, true);
auto [heightLeft, balancedLeft] = helper(root->left);
auto [heightRight, balancedRight] = helper(root->right);
int diff = abs(heightLeft-heightRight);
auto balanced = balancedLeft && balancedRight && diff < 2;
return make_pair(1+max(heightLeft, heightRight), balanced);
}
public:
bool isBalanced(TreeNode* root) {
auto [_height, balanced] = helper(root);
return balanced;
}
};
Unique Substrings in Wraparound String
no need to update previous letter because it is already updated when iterated over it.
class Solution {
public:
int findSubstringInWraproundString(string p) {
int cnt[26] = {0};
int length = 0;
int pLength = p.length();
for(int i = 0; i < pLength; ++i) {
char last = p[i] == 'a' ? 'z' : p[i]-1;
int index = p[i] - 'a';
if(i && p[i-1] != last) {
length = 0;
}
length += 1;
cnt[index] = max(cnt[index], length);
}
int answer = 0;
for(int i = 0; i < 26; ++i) answer += cnt[i];
return answer;
}
};
BTW following solution seems more efficient
class Solution {
public:
int findSubstringInWraproundString(string p) {
int length[26] = {0};
int pos = 0, len = p.length();
int currentLength = 0;
int lastChar = -1;
while(pos < len) {
int currentChar = p[pos]-'a';
int prevChar = (currentChar - 1 + 26) % 26;
if(lastChar != prevChar) {
currentLength = 0;
}
currentLength += 1;
if(length[currentChar] < currentLength) {
length[currentChar] = currentLength;
}
lastChar = currentChar;
pos += 1;
}
int answer = 0;
for(int i = 0; i < 26; ++i) {
answer += length[i];
}
return answer;
}
};
3Sum
use dfs with set
class Solution {
int len;
vector<vector<int>> twoSum(vector<int> &nums, int target, int start) {
vector<vector<int>> answer;
unordered_set<int> st;
for(int i = start; i < len; ++i) {
if(answer.size() && answer.back()[1] == nums[i]) continue;
if(st.count(nums[i])) {
answer.push_back(vector<int>{target-nums[i], nums[i]});
}
st.insert(target-nums[i]);
}
return answer;
}
vector<vector<int>> kSum(vector<int> &nums, int target, int start, int k) {
vector<vector<int>> answer;
if(nums[start] * k > target || target > nums.back() * k) return answer;
if(k == 2) return twoSum(nums, target, start);
for(int i = start; i <= len-k; ++i) {
if(i != start && nums[i] == nums[i-1]) continue;
for(auto &vec : kSum(nums, target-nums[i], i+1, k-1)) {
answer.push_back({nums[i]});
answer.back().insert(answer.back().end(), vec.begin(), vec.end());
}
}
return answer;
}
void init(vector<int> &nums) {
len = nums.size();
sort(nums.begin(), nums.end());
}
public:
vector<vector<int>> threeSum(vector<int>& nums) {
if(nums.size() < 3) return vector<vector<int>>();
init(nums);
return kSum(nums, 0, 0, 3);
}
};
4Sum
use dfs with set
class Solution {
int len;
vector<vector<int>> twoSum(vector<int> &nums, int target, int start) {
vector<vector<int>> answer;
unordered_set<int> st;
for(int i = start; i < len; ++i) {
if(answer.size() && answer.back()[1] == nums[i]) continue;
if(st.count(nums[i])) {
answer.push_back(vector<int>{target-nums[i], nums[i]});
}
st.insert(target-nums[i]);
}
return answer;
}
vector<vector<int>> kSum(vector<int> &nums, int target, int start, int k) {
vector<vector<int>> answer;
if(nums[start] * k > target || target > nums.back() * k) return answer;
if(k == 2) return twoSum(nums, target, start);
for(int i = start; i <= len-k; ++i) {
if(i != start && nums[i] == nums[i-1]) continue;
for(auto &vec : kSum(nums, target-nums[i], i+1, k-1)) {
answer.push_back({nums[i]});
answer.back().insert(answer.back().end(), vec.begin(), vec.end());
}
}
return answer;
}
void init(vector<int> &nums) {
len = nums.size();
sort(nums.begin(), nums.end());
}
public:
vector<vector<int>> fourSum(vector<int>& nums, int target) {
if(nums.size() < 4) return vector<vector<int>>();
init(nums);
return kSum(nums, target, 0, 4);
}
};
December LeetCoding Challenge 26
Description
Decode Ways
A message containing letters from A-Z
is being encoded to numbers using the following mapping:
'A' -> 1
'B' -> 2
...
'Z' -> 26
Given a non-empty string containing only digits, determine the total number of ways to decode it.
The answer is guaranteed to fit in a 32-bit integer.
Example 1:
Input: s = "12"
Output: 2
Explanation: It could be decoded as "AB" (1 2) or "L" (12).
Example 2:
Input: s = "226"
Output: 3
Explanation: It could be decoded as "BZ" (2 26), "VF" (22 6), or "BBF" (2 2 6).
Example 3:
Input: s = "0"
Output: 0
Explanation: There is no character that is mapped to a number starting with '0'. We cannot ignore a zero when we face it while decoding. So, each '0' should be part of "10" --> 'J' or "20" --> 'T'.
Example 4:
Input: s = "1"
Output: 1
Constraints:
1 <= s.length <= 100
s
contains only digits and may contain leading zero(s).
Solution
simple DP
class Solution {
public:
int numDecodings(string s) {
int len = s.length();
vector<int> dp(len+1);
dp[0] = 1;
for(int i = 0; i < len; ++i) {
if(s[i] > '0') {
dp[i+1] = dp[i];
} if(i) {
int code = (s[i-1]-'0')*10 + s[i]-'0';
if(code > 9 && code < 27) {
dp[i+1] += dp[i-1];
}
}
}
return dp.back();
}
};