[算法]力扣刷题-初级算法(一)数组

26. 删除有序数组中的重复项

给你一个有序数组 nums ,请你 原地 删除重复出现的元素,使每个元素 只出现一次 ,返回删除后数组的新长度。
不要使用额外的数组空间,你必须在 原地 修改输入数组 并在使用 O(1) 额外空间的条件下完成。
示例 2:
输入:nums = [0,0,1,1,1,2,2,3,3,4]
输出:5, nums = [0,1,2,3,4]
解释:函数应该返回新的长度 5 , 并且原数组 nums 的前五个元素被修改为 0, 1, 2, 3, 4 。不需要考虑数组中超出新长度后面的元素。
链接:https://leetcode-cn.com/problems/remove-duplicates-from-sorted-array

思路:数组已经排好序了,从第0个元素作为对比项(cur_index),对比之后的元素是否与对比项相同,相同则跳过,不相同则更新为对比项,计数count++,并赋值到第count个元素中。
时间复杂度:O(n)
空间复杂度:O(1)

int removeDuplicates(int* nums, int numsSize)
{
    
    
    if(numsSize == 0)
    {
    
    
        return 0;
    }
    short count = 1;
    short cur_index = 0;

    for(short i = 1; i<numsSize; i++)
    {
    
    
        if(nums[i] != nums[cur_index])
        {
    
    
            if(count != i)
            {
    
    
                nums[count] = nums[i];
            }
            count++;
            cur_index = i;
        }
    }
    return count;

}

122. 买卖股票的最佳时机 II

给定一个数组 prices ,其中 prices[i] 是一支给定股票第 i 天的价格。
设计一个算法来计算你所能获取的最大利润。你可以尽可能地完成更多的交易(多次买卖一支股票)。
注意:你不能同时参与多笔交易(你必须在再次购买前出售掉之前的股票)。
示例1: 输入: prices = [7,1,5,3,6,4] 输出:
7 解释: 在第 2 天(股票价格 = 1)的时候买入,在第 3 天(股票价格 = 5)的时候卖出, 这笔交易所能获得利润 = 5-1 =4 。
随后,在第 4 天(股票价格 = 3)的时候买入,在第 5 天(股票价格 = 6)的时候卖出, 这笔交易所能获得利润 = 6-3 = 3 。

链接:https://leetcode-cn.com/problems/best-time-to-buy-and-sell-stock-ii

思路:找到山峰和山谷,山峰卖出,山谷买入。山峰的特点是下一个元素开始变小,即为山峰,山谷的特点是下一个元素开始变大,即为山谷。注意最后一个交易日如果不是卖出,要把当前的持有全部卖出。
时间复杂度:O(n)
空间复杂度:O(1)

int maxProfit(int* prices, int pricesSize)
{
    
    
    int buy_prices = 0;
    int profit_count = 0;
    char buy_flag = false;
    for(short i = 1; i< pricesSize; i++)
    {
    
    
        if(prices[i] > prices[i-1] && !buy_flag)
        {
    
    
            buy_prices = prices[i-1];
            buy_flag = true;
        }
        else if(prices[i] < prices[i-1] && buy_flag)
        {
    
    
            profit_count += prices[i-1] - buy_prices;
            buy_flag = false;
        }
    }
    if(buy_flag)
    {
    
    
        profit_count += prices[pricesSize-1] - buy_prices;
    }
    return profit_count;
}

189. 轮转数组

给你一个数组,将数组中的元素向右轮转 k 个位置,其中 k 是非负数。
示例 1: 输入: nums = [1,2,3,4,5,6,7],
k = 3 输出: [5,6,7,1,2,3,4]
解释: 向右轮转 1 步: [7,1,2,3,4,5,6]
向右轮转 2 步:[6,7,1,2,3,4,5]
向右轮转 3 步: [5,6,7,1,2,3,4]
链接:https://leetcode-cn.com/problems/rotate-array

思路:

  1. 先将k对数组长度取余,因为整圈数的轮转没有意义。
  2. 整个数组反转,然后按取余后的temp_k将数组分成前后两部分,两部分再分别反转。
    时间复杂度:O(n)
    空间复杂度:O(1)
void rotate(int* nums, int numsSize, int k)
{
    
    
    int temp_k = k%numsSize;
    if(numsSize == 1 || temp_k == 0)
    {
    
    
        return;
    }
    for(int i = 0; i<numsSize/2; i++)
    {
    
    
        int temp = nums[i];
        nums[i] = nums[numsSize-i-1];
        nums[numsSize-i-1] = temp;
    }
    
    for(int i = 0; i<temp_k/2; i++)
    {
    
    
        int temp = nums[i];
        nums[i] = nums[temp_k-i-1];
        nums[temp_k-i-1] = temp;
    }
    
    for(int i = 0; i<(numsSize-temp_k)/2; i++)
    {
    
    
        int temp = nums[i+temp_k];
        nums[i+temp_k] = nums[numsSize-i-1];
        nums[numsSize-i-1] = temp;
    }

}

猜你喜欢

转载自blog.csdn.net/weixin_43854928/article/details/121315702