https://leetcode.com/problems/candy/
There are N children standing in a line. Each child is assigned a rating value.
You are giving candies to these children subjected to the following requirements:
- Each child must have at least one candy.
- Children with a higher rating get more candies than their neighbors.
What is the minimum candies you must give?
Example 1:
Input: [1,0,2]
Output: 5
Explanation: You can allocate to the first, second and third child with 2, 1, 2 candies respectively.
Example 2:
Input: [1,2,2] Output: 4 Explanation: You can allocate to the first, second and third child with 1, 2, 1 candies respectively. The third child gets 1 candy because it satisfies the above two conditions.
题目陷阱:相同等级的小孩拿糖没有要求
//双向扫描算法
class Solution {
public:
int candy(vector<int>& ratings) {
int n=ratings.size();
if(n==0){
return 0;
}
vector<int> candy(n,1);
for(int i=1;i<n;i++){ //保证从左到右非递减
if(ratings[i]>ratings[i-1]){
candy[i]=candy[i-1]+1;
}
}
for(int i=n-1;i>=1;i--){ //保证总右到左非递减
if(ratings[i-1]>ratings[i] && candy[i-1]<=candy[i]){
candy[i-1]=candy[i]+1;
}
}
int total=0;
for(auto x : candy){
total+=x;
}
return total;
}
};
//每次到下一个山峰的时候,计算之前山峰所有糖的数目
class Solution {
private:
int count(int n){
return n*(n+1)/2;
}
public:
int candy(vector<int>& ratings) {
int n=ratings.size();
if(n==0){
return 0;
}
int up=0,down=0;
int candys=0;
int new_slope=0,old_slope=0;
for(int i=1;i<n;i++){
new_slope=(ratings[i]>ratings[i-1]) ? 1 : (ratings[i]<ratings[i-1] ? -1 : 0);
if((old_slope<0 && new_slope>=0) || (old_slope>0 && new_slope==0)){
candys+=count(up)+count(down)+max(up,down);
up=0;
down=0;
}
if(new_slope>0){
up++;
}else if(new_slope<0){
down++;
}else{ //(new_slope==0)
candys++;
}
old_slope=new_slope;
}
candys+=count(up)+count(down)+max(up,down)+1;
return candys;
}
};