[算法刷题打卡]Day3

1、Leetcode-面试经典150题目6-189. 轮转数组

思路

1、要实现题目中的循环轮转数组,一个关键的公式是:(i+k)%n ,可以实现循环取数。

2、首先,第一种方法解释开辟一个额外的数组,将原来下标i的元素放到新数组下标为(i + k)mod n的位置,即轮转之后的数组。

3、nums.assign(temp.begin(),temp.end());将temp数组拷贝到nums中

//方法1 使用额外数组

class Solution {
public:
    void rotate(vector<int>& nums, int k) {
        int n = nums.size();
        vector<int> newArr(n);
        for(int i = 0;i < n;++ i)
            newArr[(i+k)%n] = nums[i];
        //将newarr数组拷贝到原数组
        nums.assign(newArr.begin(),newArr.end());
    }
};

还有另外一种方法,就是利用数组翻转,举个例子

[1,2,3,4,5,6,7]  k = 3  ------> 我们的目标 [5,6,7,     1,2,3,4]

1.第一次翻转:整个翻转 [7,6,5,4,3,2,1]

2.第二次翻转:将前面翻转过来的即前k个翻转,  [5,6,7,4,3,2,1]

3.第三次翻转:将从第k+1到结尾翻转[5,6,7,1,2,3,4]

class Solution {
public:
    void rotate(vector<int>& nums, int k) {
         k %=nums.size(); //对于数组长度小于k的情况要考虑
         reverse(nums.begin(),nums.end());
         reverse(nums.begin(),nums.begin()+k);
         reverse(nums.begin()+k,nums.end());
    }
};

知识点总结: 数学、数组、双指针


2、Leetcode-面试经典150题目7-121. 买卖股票的最佳时机

思考

1.一开始直接暴力,过了200个样例,但是后面时间超时了

const int N = 100010;
class Solution {
public:
    int maxProfit(vector<int>& prices) {
      
        int max = 0, cnt; // 最大利润
        for (int i = 0; i < prices.size(); i++) {
            for (int j = i + 1; j < prices.size();
                 j++) // 卖出时间必须大于买入时间
            {   if(prices[j] <= prices[i] || prices[j-1] >= prices[j]){
                    continue;
            }else{
                cnt = prices[j] - prices[i];
                if (cnt > max)
                    max = cnt;

            }
                
            }
        }
        return max;
    }
};

2.暴力法超时,时间复杂度O(n^2),所以必须要转换为一维的

3.用动态规划的思想,dp[i]为第i天以前的最低价,所以第i天的最大利润就是price[i]-dp[i]

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

知识点总结:数组、动态规划


3、Leetcode-面试经典150题目8-122. 买卖股票的最佳时机 II

思路:

1.状态方程如下表示,对于dp[i,0] ,可能前一天有一支股票或者前一天也没有股票。对于dp[i,1],可能前一天依然就一支股票或者前一天没有今天买入的。

2.状态规划类的问题最难想的就是状态转移方程,需要仔细思考状态是如何转移的。

3.对于本题和上题的区别,上题只用买入卖出一次,状态只有一维,只用考虑在第i天之前买入时最低价。对于本题,因为每天交易之后只可能存在手里有一支股票或者没有股票的状态,所以每天都必须要考虑有股票和没股票的状态。

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

知识点总结:数组、动态规划、贪心


每日一言:无论你的人生路途有多么曲折,都要保持一颗坚韧不拔的心,因为终点的就在前方。

2024年3月21日

softdream

  • 43
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值