Day4-LeetCode刷题(贪心算法练习)

今天是刷题的第四天,引用kuangbin大佬的话
人—我百,人十我万!追逐青春的梦想,怀着自信的心,永不放弃!
虽然可能做不到如此,但希望持续下去。

122. Best Time to Buy and Sell Stock II(easy)

原题地址
在这里插入图片描述

题目描述

  • 这道题的题意很简单,意思是每天都可以进行出售和购买股票,求最大利润
  • 输入为一个一维数组,表示每天的股价变化情况,输出是最大的利润

策略

  • 这题考虑贪心算法,可以直接暴力贪心,既然不限次数,那么只要股价明天比高,我就在第二天把它给卖了,采用的是非常短视的买入卖出策略,即只考虑两天前后股价的涨幅。当然在现实生活中,这种策略不太可行,一是现实生活中并不知道明天是否会涨还是跌,要是知道的话也不会在这里写博客了(笑哈哈哈),这种策略叫做短线,即只考虑短期收益,二是现实生活中买入卖出有手续费,所以这样频繁操作钱都进中介口袋里了(毕竟不论涨跌,买入卖出中介就有钱赚了)。

代码:

class Solution {
    
    
public:
    int maxProfit(vector<int>& prices) {
    
    
        int size = prices.size();
        int ans = 0;
        for(int i=0;i<size-1;i++){
    
    
            if(prices[i]<=prices[i+1]){
    
    
                ans += prices[i+1]-prices[i];
            }
        }
        return ans;
    }
};

406. Queue Reconstruction by Height(Medium)

原题地址
在这里插入图片描述

题目描述

  • 这道题是按高度排序队列问题,意思是说给定一群人,需要按规则把他们排好序。
  • 输入是二维数组,每一维数组有两个元素,即[hi,hk],其中hi表示该人的高度,而hk表示这个人前面不允许有hk个人比他高;输出是排好序的二维数组

策略

  • 这道题考虑贪心算法,我们按照高度从高到低先排好序,这样就可以保证待会进行操作时只需要往左边插入就可以了,因为左边都是比他高的,那么如果要满足要求的话就只需要把他往前排插入就可以了(即左边)。然后从左往右开始遍历,对每一个人的由hk这个限制条件进行验证。
  • 这里用到了比较笨的插入算法,是c语言刚学的时候教的,但刚开始竟然还王了- -,就是把前k+1的元素往后移动一个位置,再将元素插入到k的位置,实现将元素插入相应元素。但C++的vector有其他的实现方法,例如用insert实现,直接暴力遍历所有元素,将其插入到与开始相距hk的位置(即前面有hk个人比他高或和一样高),但这样虽然简单,但开辟了不必要的空间,如果数组再大一些就不能用了。另一种是用erase和insert实现的,没有上一种那么暴力,加个判断,当刚好到hk位置时,先进行erase删除当前元素,再用insert在相应位置插入,但亲测会慢一些,所以用传统简单的方法速度会快一些。

代码:

class Solution {
    
    
public:
    vector<vector<int>> reconstructQueue(vector<vector<int>>& people) {
    
    
        sort(people.begin(),people.end(),[](vector<int>& a, vector<int>& b){
    
    
            return a[0]>b[0] || (a[0]==b[0] && a[1]<b[1]);
        });
        for(int i=0; i<people.size(); i++){
    
    
            
            int cnt = people[i][1];
            for(int j=0; j<i; j++){
    
    
                if(cnt == 0){
    
    
                    auto temp = people[i];
                    for(int k=i-1;k>=j;k--){
    
    
                        people[k+1] = people[k];
                    }
                    people[j] = temp;
                    break;
                }
                cnt -= 1;
            }
        }
        return people;
    }
};

665. Non-decreasing Array(Medium)

原题地址
在这里插入图片描述

题目描述

  • 这道题的题意很简单,意思是给定一个数组,最多只能用修改一个元素使得它成为非递减数组。
  • 输入为一个一维数组,输出是是否能实现

策略

  • 这题设置一个bool变量,遍历数组中的所有元素,若当前元素比下一个元素大的话,则不满足条件,则需要进行修正,进一步,若当前元素在第一个位置或上一个元素比下一个元素大时,将其修正等于下一个元素大小,反之将下一个元素设置为当前元素大小,此时修改bool变量,下一次若还需要修改的话,则不满足条件了,直接返回false。其实算是贪心算法,就是当数组元素都相同时那就满足条件了,那么在修改的时候也可以尽可能靠近这个极端情况,设置到<=的边界,即等于条件,这样为后面的元素提供了更大的缩小空间。

代码:

class Solution {
    
    
public:
    bool checkPossibility(vector<int>& nums) {
    
    
        bool ans = false;
        int size = nums.size()-1;
        for(int i=0; i<size; i++){
    
    
            if(nums[i] > nums[i+1]){
    
    
                if(ans){
    
    
                    return false;
                }else{
    
    
                    if(i==0 || nums[i+1]>=nums[i-1])
                        nums[i] = nums[i+1];
                    else
                        nums[i+1] = nums[i];
                }
                ans = true;
            }
        }
        return true;
    }
};

猜你喜欢

转载自blog.csdn.net/Geek_/article/details/113620541
今日推荐