LeetCode:135. 分發糖果 老師想給孩子們分發糖果,有 N 個孩子站成了一條直線,老師會根據每個孩子的表現,預先給他們評分。 你需要按照以下要求,幫助老師給這些孩子分發糖果: 每個孩子至少分配到 1 個糖果。 相鄰的孩子中,評分高的孩子必須獲得更多的糖果。 那麼這樣下來,老師至少需要準備多 ...
LeetCode:135. 分發糖果
老師想給孩子們分發糖果,有 N 個孩子站成了一條直線,老師會根據每個孩子的表現,預先給他們評分。
你需要按照以下要求,幫助老師給這些孩子分發糖果:
- 每個孩子至少分配到 1 個糖果。
- 相鄰的孩子中,評分高的孩子必須獲得更多的糖果。
那麼這樣下來,老師至少需要準備多少顆糖果呢?
示例 1:
輸入: [1,0,2]
輸出: 5
解釋: 你可以分別給這三個孩子分發 2、1、2 顆糖果。
示例 2:
輸入: [1,2,2]
輸出: 4
解釋: 你可以分別給這三個孩子分發 1、2、1 顆糖果。
第三個孩子只得到 1 顆糖果,這已滿足上述兩個條件。
來源:力扣(LeetCode)
鏈接:https://leetcode-cn.com/problems/candy
著作權歸領扣網路所有。商業轉載請聯繫官方授權,非商業轉載請註明出處。
解題思路
方法一:一趟遍歷
- 演算法:
- 初始化:i=0(用於迭代評分數組ratings)
- 若
i<ratings.size()
,進行迴圈,考慮以下三種情況:
2.1 若i==0 或 ratings[i]==ratings[i-1]
(第一個小孩或者第i個小孩與第i-1個 小孩的評分相同,註意:只要求評分高的學生比相鄰評分低的同學糖果多)
則:candies[i]=0; i=i+1;
2.2 若ratings[i]>ratings[i-1]
(評價高清前一個小孩,可多發一個糖果)
則:candies[i]=candies[i-1]+1; i=i+1;
2.3 若ratings[i]<ratings[i-1]
(評價低於前一個小孩)
則:找到評價嚴格遞減序列ratings[i-1: j]
,此時需要修正candies[i-1]
的值,candies[i-1]=max(candies[i-1], j-i+2); candies[i:j]=[j-i+1,...,1]; i=j+1;
- 將數組candies的所有元素相加所得結果,即為所需最少糖果數
- 代碼:
class Solution {
public:
int candy(vector<int>& ratings) {
int n=ratings.size();
vector<int> candies(n);
for(int i=0; i<n;){
if(i==0 || ratings[i]==ratings[i-1]){
candies[i]=1;
i++;
}
else if(ratings[i]>ratings[i-1]){
candies[i]=candies[i-1]+1;
i++;
}
else{
int j=i+1;
while(j<n && ratings[j]<ratings[j-1]) j++;
int len=j-i;
candies[i-1]=max(candies[i-1], len+1);
for(int k=i; k<j; k++)
candies[k]=len--;
i=j;
}
}
return accumulate(candies.begin(), candies.end(), 0);
}
};
- 時空分析
時間複雜度:一趟遍歷,O(n)
空間複雜度:使用一維數組記錄每個小孩的糖果數,O(n)