代码随想录训练营第二十九天 134加油站 135分发糖果 860柠檬水找零 406根据身高重建队列

第一题:

原题链接:134. 加油站 - 力扣(LeetCode)

思路:

需要三个变量,一个变量start记录结果也就是出发的第一个加油站,一个变量curSum来记录此时加油耗油后剩余的油量,如果发现curSum小于0的话就直接从当前加油站的下一个加油站作为第一个加油站重新计算;一个变量totalSum来记录行驶完一圈后剩余的油量,如果小于0说明行驶不了一圈返回-1;

代码如下:

class Solution {
public:
    int canCompleteCircuit(vector<int>& gas, vector<int>& cost) {
        int start = 0;
        int curSum = 0;
        int totalSum = 0;
        for(int i = 0; i < gas.size(); i++){
            curSum += gas[i] - cost[i];
            totalSum += gas[i] - cost[i];
            if(curSum < 0){
                start = i + 1;
                curSum = 0;
            }
        }
        if(totalSum < 0) return -1;
        return start;
    }
};

第二题:

原题链接:135. 分发糖果 - 力扣(LeetCode)

思路:

先从左向右遍历记录右孩子比左孩子多的情况,然后再从右向左遍历记录左孩子比右孩子高分的情况。从右向左遍历的时候要基于从左向右遍历后的结果进行计算。

两者比较完取最大值。

代码如下:

class Solution {
public:
    int candy(vector<int>& ratings) {
        vector<int> res(ratings.size(), 1);
        for(int i = 1; i < ratings.size(); i++){
            if(ratings[i] > ratings[i - 1]){
                res[i] = res[i - 1] + 1;
            }
        }
        for(int i = ratings.size() - 2; i >= 0; i--){
            if(ratings[i] > ratings[i + 1]){
                res[i] = max(res[i], res[i + 1] + 1);
            }
        }
        int sum = 0;
        for(int i = 0; i < res.size(); i++){
            sum += res[i];
        }
        return sum;
    }
};

第三题:

原题链接:860. 柠檬水找零 - 力扣(LeetCode)

思路:

收到五块直接收下,

收到十块需要看有没有五块,没有五块直接返回false,如果有五块减一。

收到二十块,如果没有五块直接返回false,如果没有十块且五块少于3张,也返回false。找零的时候先找十块的,没有十块的再找五块。

代码如下:

class Solution {
public:
    bool lemonadeChange(vector<int>& bills) {
        unordered_map<int, int> map;
        for(int i = 0; i < bills.size(); i++){
            if(bills[i] == 5) map[5] += 1;
            if(bills[i] == 10){
                map[10] += 1;
                if(map[5] == 0) return false;
                map[5] -= 1;
            }
            if(bills[i] == 20){
                map[20] += 1;
                if(map[5] == 0) return false;
                if(map[10] == 0 && map[5] < 3) return false;
                if(map[10]){
                    map[10]--;
                    map[5]--;
                }else{
                    map[5] -= 3;
                }
            }
        }
        return true;
    }
};

第四题:

原题链接:406. 根据身高重建队列 - 力扣(LeetCode)

先根据身高进行从大到小的排序,如果身高相同就根据k进行从小到大排序。

然后遍历数组,根据k的值插入到结果数组中。

按照身高排序之后,优先按身高高的people的k来插入,后序插入节点也不会影响前面已经插入的节点,最终按照k的规则完成了队列。

代码如下:

class Solution {
public:
    static bool cmp(vector<int> a, 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);
        vector<vector<int>> res;
        for(int i = 0; i < people.size(); i++){
            int position = people[i][1];
            res.insert(res.begin() + position, people[i]);
        }
        return res;
    }
};

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值