[Code Random Records] Brushing Questions Day51&Day52

 day51

1. The best time to buy and sell stocks includes a freezing period

309. The best time to buy and sell stocks includes a freezing period

1. The meaning of the dp array: dp[i][0] is the maximum value of the stock sold on the i-th day; dp[i][1] is the maximum value of the stock held on the i-th day

2. The condition of the dp array: due to the freezing period, the condition of the dp array has changed. There are two situations for the maximum value of the stock sold on the i-th day. One is the maximum value of the stock sold last time, and the other is the maximum value of the stock sold the previous time. Then the condition is dp[i][0]= max(dp[i-1][0],dp[i-1][1]+prices[i]). There are also two types of maximum value of stocks held on the i-th day, one is the maximum value of stocks held last time, and the other is the maximum value of stocks sold two days ago (because the stocks held on the previous day cannot be sold during the freezing period), then The condition is dp[i][1]=max(dp[i-1][1],dp[i-2][0]-prices[i]);

3. Initialization: dp[0][0]=0 and dp[0][1]=-prices[0] have nothing to say. However, since our shareholding logic becomes i-2, that is to say, if traversing from 1 will cause out-of-bounds access, then we need to set the value of position 1 in advance. The logic of position 1 does not need to consider the freezing period, so continue The understanding of the dp array conditions in the previous questions naturally knows that the initialization is: dp[1][0]=max(dp[0][0],dp[0][1]+prices[1]) and dp[1] ][1]=max(dp[0][1],dp[0][0]-prices[1]);

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

2. The best time to buy and sell stocks includes handling fees

714. The best time to buy and sell stocks includes handling fees

Similar to 122. Best Time to Buy and Sell Stocks II

Hesitation This question has added the so-called "handling fee", so in fact, the condition requires that the handling fee should be subtracted when selling stocks. To put it bluntly, it is a little cheaper on the basis of the original selling, but we are looking for selling The max value varies with the meaning of the dp array. The meaning of the array is still the maximum value, but there may be frequent transactions, and the stock method that was originally frequently traded may be smaller, but the dp array is still the most valuable method to obtain the inclusion minus the handling fee through each purchase and sale , then the condition naturally only needs to subtract the fee, so it becomes dp[i][0]=max(dp[i-1][0],dp[i-1][1]+prices[i] -fee)

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

3. Summary

I think the core of stock problems is to determine what the d array represents, and it should be defined in this way to include all situations.

1. For example, the initial stock problem is just to find the maximum value, then we don't need to consider the problem of accumulation, and directly take the maximum value for comparison.

2. For example, the cumulative maximum value in the back is actually to add the last value and the current sold stock value to find the maximum value, which is one step more processing logic than the initial maximum value.

3. The number of purchases is also limited, so the dp array we set needs to represent the definition of the nth shareholding or selling. Finally, conditional judgments are made based on the upper and lower relationships

So in fact, it is necessary to clarify the topic conditions first, find a suitable dp array definition, whether to buy multiple times or once. Then look at the given conditions to simulate the dp array conditions. In fact, the idea of ​​simulation is very simple. For a single condition, it is to look at the relationship between the previous time and the current time; for the whole, it is to look at the relationship between each layer. After the condition is determined, corresponding initialization is performed according to the condition. The initial value of the initialization must meet the description of the topic, the definition of dp, and the corresponding operation specification of the dp array. Finally, it is necessary to observe whether special initialization is required.

Day52

 1. Longest increasing subsequence

300. Longest Increasing Subsequence

1. Each number has a length of 1, so the initialization is very simple, and all are set to 1 directly.

2. The meaning of the dp array: the longest increasing subsequence of the number corresponding to the i-th position

3. Condition: At the i-th position, we have to look forward and traverse each previous number. If the number at the j position is smaller than the i position, then we can actually consider updating. The idea of ​​​​the update is to find the longest, Then it is necessary to compare the current length with the length of the previous jth position + 1, and the natural condition is dp[i]=max(dp[i],dp[j]+1)

4. Since our dp array stores the longest increasing subsequence of numbers corresponding to i, rather than the longest overall, we need a ret to record the longest number, and finally return

class Solution {
public:
    int lengthOfLIS(vector<int>& nums) {
        vector<int>dp(nums.size(),1);
        int ret = 1;
        for(int i=1;i<nums.size();i++)
        {
            for(int j=i-1;j>=0;j--)
            {
                if(nums[i]>nums[j])
                {
                    dp[i]=max(dp[i],dp[j]+1);
                }
            }
            ret=max(ret,dp[i]);
        }
        return ret;
    }
};

2. The longest continuous increasing sequence

674. Longest Continuous Increasing Sequence

This question is actually comparing the number at the current position with the number corresponding to the previous position. If it is greater than the previous dp update, dp[i]=dp[i-1]+1 is relatively simple, so I won’t go into details

class Solution {
public:
    int findLengthOfLCIS(vector<int>& nums) {
        vector<int>dp(nums.size(),1);
        int ret = 1;
        for(int i=1;i<nums.size();i++)
        {
            if(nums[i]>nums[i-1])
                dp[i]=dp[i-1]+1;
            ret=max(ret,dp[i]);
        }
        return ret;
    }
};

3. Longest repeating subarray

718. Longest Repeating Subarray

1. The meaning of the dp array: dp[i][j] is the largest repeated substring at the position where i-1 and j-1 are compared

2. According to the above meaning, we know that the conditional comparison is whether the numbers of nums1[i-1] and nums2[j-1] are the same. If they are the same, it means that the length at this time is the last comparison between i-1 and j- Add one to the case of the longest repeated sub-array of the two numbers before 1, that is, dp[i][j]=dp[i-1][j-1]+1;

3. Then the reason why the dp array is defined as the situation at i-1 and j-1, then the numbers corresponding to dp[i][0] and dp[0][j] in the initialization should be 0, because they are not The actual corresponding number is matched. If we define as i position and j position, then we need to traverse all the cases where the two arrays each take a number for initialization, and the cost of this definition is too high.

class Solution {
public:
    int findLength(vector<int>& nums1, vector<int>& nums2) {
        int ret = 0;
        vector<vector<int>>dp(nums1.size()+1,vector<int>(nums2.size()+1,0));
        for(int i=1;i<=nums1.size();i++)
        {
            for(int j=1;j<=nums2.size();j++)
            {
                if(nums1[i-1]==nums2[j-1])
                {
                    dp[i][j]=dp[i-1][j-1]+1;
                }
                ret=max(ret,dp[i][j]);
            }
        }
        return ret;
    }
};

Guess you like

Origin blog.csdn.net/m0_63488627/article/details/131102945