[Leetcode 60 days with refresh] day34 greedy - 860. Lemonade change, 406. Rebuild the queue according to height


  topic:

860. Lemonade Change

At the lemonade stand, a glass of lemonade sells for  5 US dollars. Customers line up to buy your product, (in  bills order of bill payment) one drink at a time.

Each customer just buys a glass of lemonade and pays you  5 dollars, 10 dollars, or  20 dollars. You have to give each customer the correct change, which means the net transaction is each customer paying you  5 dollars.

Note that you don't have any change on hand at first.

Give you an array of integers  bills , which  bills[i] is  i the bill paid by the first customer. If you can give each customer correct change, return  true , otherwise return  false .

Example 1:

Input: bills = [5,5,5,10,20]
 Output: true
 Explanation:
 For the first 3 customers, we collect 3 $5 bills in order.
For the 4th customer, we take a $10 bill and give back $5.
With the 5th customer, we return a $10 bill and a $5 bill.
Since all customers got correct change, we output true.

Example 2:

Input: bills = [5,5,10,10,20]
 Output: false
 Explanation:
For the first 2 customers, we collect 2 $5 bills in sequence.
For the next 2 customers, we take a $10 bill and give back $5.
For the last customer, we can't refund the $15 because we only have two $10 bills right now.
Since not every customer gets the correct change, the answer is false.

hint:

  • 1 <= bills.length <= 105
  • bills[i] either  5 or  10 _ 20 

Thinking process and knowledge points: 

There are three situations:

  • Situation 1: The bill is 5, just accept it.
  • Situation 2: The bill is 10, a 5 is consumed, and a 10 is added
  • Situation 3: The bill is 20, first consume a 10 and a 5, if not enough, consume three more 5

At this time, everyone found that situation 1 and situation 2 are fixed strategies, and we don’t need to analyze them, and the only uncertainty is actually situation 3.

In case three, the logic is not complicated or even pure simulation is enough. In fact, case three is greedy.

When the bill is 20, why should you give priority to consuming a 10 and a 5?

Because USD 10 can only give change to bill 20, while USD 5 can give change to bill 10 and bill 20, USD 5 is more versatile!

Therefore, the local optimum: When encountering a bill of 20, spend 10 dollars first, and complete this change. Global Optimal: Complete the change of all bills.


 answer:

class Solution {
public:
    bool lemonadeChange(vector<int>& bills) {
        int five = 0, ten = 0, twenty = 0;
        for (int bill : bills) {
            // 情况一
            if (bill == 5) five++;
            // 情况二
            if (bill == 10) {
                if (five <= 0) return false;
                ten++;
                five--;
            }
            // 情况三
            if (bill == 20) {
                // 优先消耗10美元,因为5美元的找零用处更大,能多留着就多留着
                if (five > 0 && ten > 0) {
                    five--;
                    ten--;
                    twenty++; // 其实这行代码可以删了,因为记录20已经没有意义了,不会用20来找零
                } else if (five >= 3) {
                    five -= 3;
                    twenty++; // 同理,这行代码也可以删了
                } else return false;
            }
        }
        return true;
    }
};

  topic:

406. Rebuild Queue Based on Height

Suppose a group of people in random order stand in a queue, and the array  people represents the attributes of some people in the queue (not necessarily in order). Each  people[i] = [hi, ki] represents  i the height of the first person  hi , and there   is  exactly one  person whose ki height is greater than or equal to  .hi

Please reconstruct and return  people the queue represented by the input array. The returned queue should be formatted as an array  queue , where  is  the property of the first person queue[j] = [hj, kj] in the queue  (  the person at the front of the queue).jqueue[0]

Example 1:

Input: people = [[7,0],[4,4],[7,1],[5,0],[6,1],[5,2]]
 Output: [[5,0], [7,0],[5,2],[6,1],[4,4],[7,1]]
 explained:
The person numbered 0 has a height of 5, and there is no person who is taller or the same in front of him.
The person numbered 1 has a height of 7, and there is no person who is taller or the same in front of him.
The height of the person numbered 2 is 5, and there are 2 people with higher or the same height in front of him, that is, people numbered 0 and 1.
The height of the person numbered 3 is 6, and there is 1 person who is taller or the same height in front of him, that is, the person numbered 1.
The height of the person numbered 4 is 4, and there are 4 people with higher or the same height in front of him, that is, people numbered 0, 1, 2, and 3.
The height of the person numbered 5 is 7, and there is 1 person who is taller or the same height in front of him, that is, the person numbered 1.
So [[5,0],[7,0],[5,2],[6,1],[4,4],[7,1]] is the reconstructed queue.

Example 2:

Input: people = [[6,0],[5,0],[4,0],[3,2],[2,2],[1,4]]
 Output: [[4,0], [5,0],[2,2],[3,2],[1,4],[6,0]]

hint:

  • 1 <= people.length <= 2000
  • 0 <= hi <= 106
  • 0 <= ki < people.length
  • Topic data ensures that queues can be rebuilt

Thinking process and knowledge points: 

If you sort from small to large according to k, after sorting, you will find that the arrangement of k does not meet the conditions, and the height does not meet the conditions, and neither of the two dimensions has been determined.

Then sort by the height h, the height must be arranged from large to small (if the height is the same, the small k stands in front), so that the tall ones are in the front.

At this point, we can determine a dimension, which is height, and the previous nodes must be higher than this node

After sorting by height from largest to smallest:

Local Optimal: Priority to insert according to the k of the tallest people. The people after the insert operation satisfies the queue property

Global optimal: insert operations are completed at the end, and the entire queue satisfies the property of the title queue

The local optimum can lead to the global optimum. If no counterexample can be found, then try to be greedy.


 answer:

class Solution {
public:
    // 身高从大到小排(身高相同k小的站前面)
    static bool cmp(const vector<int>& a, const vector<int>& b) {
        if (a[0] == b[0]) return a[1] < b[1];
        return a[0] > b[0];
    }
    vector<vector<int>> reconstructQueue(vector<vector<int>>& people) {
        sort (people.begin(), people.end(), cmp);
        list<vector<int>> que; // list底层是链表实现,插入效率比vector高的多
        for (int i = 0; i < people.size(); i++) {
            int position = people[i][1]; // 插入到下标为position的位置
            std::list<vector<int>>::iterator it = que.begin();
            while (position--) { // 寻找在插入位置
                it++;
            }
            que.insert(it, people[i]);
        }
        return vector<vector<int>>(que.begin(), que.end());
    }
};

Welcome to like, bookmark, comment, your encouragement is the biggest motivation for my creation! (๑╹◡╹)ノ"""

Copyright statement: This article is an original article of CSDN blogger "Dumengjiu", which follows the CC 4.0 BY-SA copyright agreement. For reprinting, please attach the original source link and this statement.
Original link: Dumengjiu's blog_CSDN blog-csdn domain blogger

Guess you like

Origin blog.csdn.net/weixin_53310927/article/details/131388354