2021-01-31 Daily-Challenge
Today is Sunday, I gonna review the tasks I've done this week, and finish today's leetcode's January LeetCoding Challenge with cpp
.
BTW, I participated in Weekly Contest 226.
January LeetCoding Challenge 31
Description
Next Permutation
Implement next permutation, which rearranges numbers into the lexicographically next greater permutation of numbers.
If such an arrangement is not possible, it must rearrange it as the lowest possible order (i.e., sorted in ascending order).
The replacement must be in place and use only constant extra memory.
Example 1:
Input: nums = [1,2,3]
Output: [1,3,2]
Example 2:
Input: nums = [3,2,1]
Output: [1,2,3]
Example 3:
Input: nums = [1,1,5]
Output: [1,5,1]
Example 4:
Input: nums = [1]
Output: [1]
Constraints:
1 <= nums.length <= 100
0 <= nums[i] <= 100
Solution
...
class Solution {
public:
void nextPermutation(vector<int>& nums) {
next_permutation(nums.begin(), nums.end());
}
};
class Solution {
public:
void nextPermutation(vector<int>& nums) {
int len = nums.size();
int pos = len - 1;
while(pos && nums[pos] <= nums[pos-1]) --pos;
if(!pos) {
reverse(nums.begin(), nums.end());
return;
}
int swapPos = len - 1;
--pos;
while(nums[swapPos] <= nums[pos]) swapPos -= 1;
swap(nums[swapPos], nums[pos]);
reverse(nums.begin() + pos + 1, nums.end());
}
};
Weekly Contest 226
5654. Maximum Number of Balls in a Box
You are working in a ball factory where you have n
balls numbered from lowLimit
up to highLimit
inclusive (i.e., n == highLimit - lowLimit + 1
), and an infinite number of boxes numbered from 1
to infinity
.
Your job at this factory is to put each ball in the box with a number equal to the sum of digits of the ball's number. For example, the ball number 321
will be put in the box number 3 + 2 + 1 = 6
and the ball number 10
will be put in the box number 1 + 0 = 1
.
Given two integers lowLimit
and highLimit
, return the number of balls in the box with the most balls.
Example 1:
Input: lowLimit = 1, highLimit = 10
Output: 2
Explanation:
Box Number: 1 2 3 4 5 6 7 8 9 10 11 ...
Ball Count: 2 1 1 1 1 1 1 1 1 0 0 ...
Box 1 has the most number of balls with 2 balls.
Example 2:
Input: lowLimit = 5, highLimit = 15
Output: 2
Explanation:
Box Number: 1 2 3 4 5 6 7 8 9 10 11 ...
Ball Count: 1 1 1 1 2 2 1 1 1 0 0 ...
Boxes 5 and 6 have the most number of balls with 2 balls in each.
Example 3:
Input: lowLimit = 19, highLimit = 28
Output: 2
Explanation:
Box Number: 1 2 3 4 5 6 7 8 9 10 11 12 ...
Ball Count: 0 1 1 1 1 1 1 1 1 2 0 0 ...
Box 10 has the most number of balls with 2 balls.
Constraints:
1 <= lowLimit <= highLimit <= 105
Solution
brute force
class Solution {
public:
int countBalls(int lowLimit, int highLimit) {
vector<int> count(100);
for(int i = lowLimit; i <= highLimit; ++i) {
int c = i;
int sum = 0;
while(c) {
sum += c % 10;
c /= 10;
}
count[sum] += 1;
}
return *max_element(count.begin(), count.end());
}
};
5665. Restore the Array From Adjacent Pairs
There is an integer array nums
that consists of n
unique elements, but you have forgotten it. However, you do remember every pair of adjacent elements in nums
.
You are given a 2D integer array adjacentPairs
of size n - 1
where each adjacentPairs[i] = [ui, vi]
indicates that the elements ui
and vi
are adjacent in nums
.
It is guaranteed that every adjacent pair of elements nums[i]
and nums[i+1]
will exist in adjacentPairs
, either as [nums[i], nums[i+1]]
or [nums[i+1], nums[i]]
. The pairs can appear in any order.
Return the original array nums
. If there are multiple solutions, return any of them.
Example 1:
Input: adjacentPairs = [[2,1],[3,4],[3,2]]
Output: [1,2,3,4]
Explanation: This array has all its adjacent pairs in adjacentPairs.
Notice that adjacentPairs[i] may not be in left-to-right order.
Example 2:
Input: adjacentPairs = [[4,-2],[1,4],[-3,1]]
Output: [-2,4,1,-3]
Explanation: There can be negative numbers.
Another solution is [-3,1,4,-2], which would also be accepted.
Example 3:
Input: adjacentPairs = [[100000,-100000]]
Output: [100000,-100000]
Constraints:
nums.length == n
adjacentPairs.length == n - 1
adjacentPairs[i].length == 2
2 <= n <= 105
-105 <= nums[i], ui, vi <= 105
- There exists some
nums
that hasadjacentPairs
as its pairs.
Solution
find a start then build the array
class Solution {
public:
vector<int> restoreArray(vector<vector<int>>& adjacentPairs) {
unordered_map<int, int> degree;
unordered_map<int, vector<int>> neighbors;
for(auto &p : adjacentPairs) {
degree[p[0]] += 1;
degree[p[1]] += 1;
neighbors[p[0]].push_back(p[1]);
neighbors[p[1]].push_back(p[0]);
}
queue<int> q;
for(auto [num, cnt] : degree) {
if(cnt == 1) {
q.push(num);
// reuse as visit
degree[num] = 0;
break;
}
}
vector<int> answer(adjacentPairs.size()+1);
int count = 0;
while(!q.empty()) {
int cur = q.front();
q.pop();
answer[count++] = cur;
for(auto n : neighbors[cur]) {
if(degree[n] != 0) {
degree[n] = 0;
q.push(n);
}
}
}
return move(answer);
}
};
5667. Can You Eat Your Favorite Candy on Your Favorite Day?
You are given a (0-indexed) array of positive integers candiesCount
where candiesCount[i]
represents the number of candies of the ith
type you have. You are also given a 2D array queries
where queries[i] = [favoriteTypei, favoriteDayi, dailyCapi]
.
You play a game with the following rules:
- You start eating candies on day
**0**
. - You cannot eat any candy of type
i
unless you have eaten all candies of typei - 1
. - You must eat at least one candy per day until you have eaten all the candies.
Construct a boolean array answer
such that answer.length == queries.length
and answer[i]
is true
if you can eat a candy of type favoriteTypei
on day favoriteDayi
without eating more than dailyCapi
candies on any day, and false
otherwise. Note that you can eat different types of candy on the same day, provided that you follow rule 2.
Return the constructed array answer
.
Example 1:
Input: candiesCount = [7,4,5,3,8], queries = [[0,2,2],[4,2,4],[2,13,1000000000]]
Output: [true,false,true]
Explanation:
1- If you eat 2 candies (type 0) on day 0 and 2 candies (type 0) on day 1, you will eat a candy of type 0 on day 2.
2- You can eat at most 4 candies each day.
If you eat 4 candies every day, you will eat 4 candies (type 0) on day 0 and 4 candies (type 0 and type 1) on day 1.
On day 2, you can only eat 4 candies (type 1 and type 2), so you cannot eat a candy of type 4 on day 2.
3- If you eat 1 candy each day, you will eat a candy of type 2 on day 13.
Example 2:
Input: candiesCount = [5,2,6,4,1], queries = [[3,1,2],[4,10,3],[3,10,100],[4,100,30],[1,3,1]]
Output: [false,true,true,false,false]
Constraints:
1 <= candiesCount.length <= 105
1 <= candiesCount[i] <= 105
1 <= queries.length <= 105
queries[i].length == 3
0 <= favoriteTypei < candiesCount.length
0 <= favoriteDayi <= 109
1 <= dailyCapi <= 109
Solution
be careful, maybe overflow
class Solution {
public:
vector<bool> canEat(vector<int>& candiesCount, vector<vector<int>>& queries) {
int len = candiesCount.size();
vector<long long> prefix(candiesCount.size()+1);
for(int i = 1; i <= len; ++i) prefix[i] = prefix[i-1] + candiesCount[i-1];
int qlen = queries.size();
vector<bool> answer(qlen);
for(int i = 0; i < qlen; ++i) {
long long type = queries[i][0];
long long day = queries[i][1];
long long cap = queries[i][2];
long long mmax = 1LL * (day+1) * cap;
long long mmin = 1LL * (day+1);
answer[i] = (mmin <= prefix[type+1]) && (mmax > prefix[type]);
}
return move(answer);
}
};
5666. Palindrome Partitioning IV
Given a string s
, return true
if it is possible to split the string s
into three non-empty palindromic substrings. Otherwise, return false
.
A string is said to be palindrome if it the same string when reversed.
Example 1:
Input: s = "abcbdd"
Output: true
Explanation: "abcbdd" = "a" + "bcb" + "dd", and all three substrings are palindromes.
Example 2:
Input: s = "bcbddxy"
Output: false
Explanation: s cannot be split into 3 palindromes.
Constraints:
3 <= s.length <= 2000
s
consists only of lowercase English letters.
Solution
enumerate all possible palindromes, and enumerate all possible length of three palindromes.
class Solution {
public:
bool checkPartitioning(string s) {
int len = s.length();
vector<vector<bool>> palin(len+1, vector<bool>(len+1));
for(int i = 0; i < len; ++i) {
palin[i][i+1] = true;
for(int j = 1; i-j >= 0 && i+j < len; ++j) {
if(s[i-j] == s[i+j]) palin[i-j][i+j+1] = true;
else break;
}
for(int j = 1; i-j+1 >= 0 && i+j < len; ++j) {
if(s[i-j+1] == s[i+j]) palin[i-j+1][i+j+1] = true;
else break;
}
}
for(int i = 1; i < len-1; ++i) {
if(!palin[0][i]) continue;
for(int j = 1; j+i < len; ++j) {
if(palin[i][i+j] && palin[i+j][len]) return true;
}
}
return false;
}
};