学习笔记@代码随想录day2:有序数组的平方 ,长度最小的子数组,螺旋矩阵

学习笔记@代码随想录day2:有序数组的平方 ,长度最小的子数组,螺旋矩阵

有序数组的平方

学习前写的暴力算法

class Solution:
    def sortedSquares(self, nums: List[int]) -> List[int]:
        #自己的方法,先计算后排序
        for i in range(len(nums)):
            nums[i]=nums[i]*nums[i]
        for i in range(len(nums)):
            for j in range(len(nums)):
                if nums[i]<nums[j]:
                    m=nums[i]
                    nums[i]=nums[j]
                    nums[j]=m
        return nums

太过暴力导致在力扣上长输入超时/(ㄒoㄒ)/~~
调用python排序方法sort解决排序问题

class Solution:
    def sortedSquares(self, nums: List[int]) -> List[int]:
        # #自己的方法,先计算后排序
        # for i in range(len(nums)):
        #     nums[i]=nums[i]*nums[i]
        # for i in range(len(nums)):
        #     for j in range(len(nums)):
        #         if nums[i]<nums[j]:
        #             m=nums[i]
        #             nums[i]=nums[j]
        #             nums[j]=m
        # return nums
        for i in range(len(nums)):
            nums[i]=nums[i]*nums[i]
        #print(nums)
        nums.sort()
        return nums

扩展学习
1.sorted() 函数可以对任何可迭代对象进行排序,包括列表、元组和字符串等。该函数会返回一个新的有序列表,原始列表不会被修改。
2.sort() 方法是列表对象的一个方法,可以对列表进行原地排序。即原始列表会被修改,而不是返回一个新的列表。
要指定降序排序,可以在 sorted() 函数或 sort() 方法中传递一个 reverse=True 参数。
这种方法的时间复杂度是这个时间复杂度是 O(n + nlogn), 可以说是O(nlogn)的时间复杂度。

下面用双指针思想来解决这个问题:

首先,排序的数组是有序数组,所以最大值从数组两边产生,所以考虑用双指针来解决这个问题。
下边是我看了视频和文档讲解后自己写的双指针法:

class Solution:
    def sortedSquares(self, nums: List[int]) -> List[int]:
        #双指针法
        new_nums=[None]*len(nums)
        i=0
        j=len(nums)-1
        k=len(nums)-1
        while i<=j:
            #最大的数值在数组两边产生
            if nums[i]* nums[i]>nums[j]* nums[j]:
                #如果最大值在左边,新数组中的最大值就等于左边的值
                new_nums[k]=nums[i]* nums[i]
                k-=1
                #比较剩下的数组,此时左边的少一位,所以i+1
                i+=1
            else:
                #此时最大值在右边,右边的数少一位,j-1
                new_nums[k]=nums[j]* nums[j]
                k-=1
                j=j-1
        return new_nums

代码随想录的双指针法

(版本一)双指针法
class Solution:
    def sortedSquares(self, nums: List[int]) -> List[int]:
        l, r, i = 0, len(nums)-1, len(nums)-1
        res = [float('inf')] * len(nums) # 需要提前定义列表,存放结果
        while l <= r:
            if nums[l] ** 2 < nums[r] ** 2: # 左右边界进行对比,找出最大值
                res[i] = nums[r] ** 2
                r -= 1 # 右指针往左移动
            else:
                res[i] = nums[l] ** 2
                l += 1 # 左指针往右移动
            i -= 1 # 存放结果的指针需要往前平移一位
        return res

总结: 掌握了双指针算法的思想,但是一些基础需要多加巩固。
拓展: python里求平方用两个*号或pow(x,2),求开方用 math.sqrt()。

长度最小的子数组

力扣209:

'''
给定一个含有 n 个正整数的数组和一个正整数 target 。
找出该数组中满足其和 ≥ target 的长度最小的 连续子数组
 [numsl, numsl+1, ..., numsr-1, numsr] ,并返回其长度。如果不存在符合条件的子数组,返回 0 。
 '''

这个题尝试自己写时,第一直觉就是先把连续的数组分离出来,再求和与target作比较。
遇到的第一个问题是:怎么把有序数组分离出来成为子数组?
本来想着先判断连续再来想下一步,但是判断连续就卡住了,写不出来/(ㄒoㄒ)/~~

看了讲解,再看来下题目,原来是我理解错了,连续子数组指的是数组连续,而不是数组的值连续/(ㄒoㄒ)/~~

看了讲解后自己写的代码

class Solution:
    def minSubArrayLen(self, target: int, nums: List[int]) -> int:
        i=0#起始位置
        sum_list=0#用于求子数组的和
        min_s=10^9#假设初始的子数组长度为这么大

        #滑动窗口思想,用双指针来遍历数组,一个遍历数组的起始位置,一个遍历数组的终止位置
        for j in range(len(nums)):
            #j表示终止位置
            sum_list+=nums[j]
            #print(sum_list)

            while sum_list>=target:
                subl=j-i+1
                #当和大于目标值的时候,求子数组的长度并和当前最小的子数组比较,选择最小的子数组
                min_s=min(min_s,subl)
                sum_list=sum_list-nums[i]#此时已经达到条件,要开始查找下一个子数组,初值指针移动一位,所以要减去前一个值
                i=+1
        return min_s

出现问题:在本地运行结果是2,但在力扣上结果出错,我不理解!!!!(todo:明天来查找问题
随想录给的代码

(版本一)滑动窗口法
class Solution:
    def minSubArrayLen(self, s: int, nums: List[int]) -> int:
        l = len(nums)
        left = 0
        right = 0
        min_len = float('inf')
        cur_sum = 0 #当前的累加值
        
        while right < l:
            cur_sum += nums[right]
            
            while cur_sum >= s: # 当前累加值大于目标值
                min_len = min(min_len, right - left + 1)
                cur_sum -= nums[left]
                left += 1
            
            right += 1
        
        return min_len if min_len != float('inf') else 0

总结 思想掌握了,但是代码写得好像不够对,明天再过一遍!

螺旋矩阵

没有时间自己写代码了,先过下螺旋矩阵的思想:
看成很多正方形,按上下左右边的顺序来填数,遵循左闭右开原则,把每条边的最后一个节点留给下一条边处理。
主要代码思想:
1.判定迭代次数,n//2,暂时是按照3的时候迭代一次,4迭代两次,5两次,6三次
2.奇数时中间填最后一个数n^2
3.4层循坏,表示4条边,四条边循坏结束后,要更新迭代次数,更新下一个开始的小正方形左上的位置坐标。
明日补上自己写的代码!

总结

今天的题比昨天难度大,主要没有预留好时间,暂时先掌握了基本算法思想,明天或者后天把代码补上,加油!
参考链接:https://programmercarl.com/0209.%E9%95%BF%E5%BA%A6%E6%9C%80%E5%B0%8F%E7%9A%84%E5%AD%90%E6%95%B0%E7%BB%84.html#%E6%BB%91%E5%8A%A8%E7%AA%97%E5%8F%A3

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值