LeetCode笔记:Weekly Contest 286

Posted Espresso Macchiato

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了LeetCode笔记:Weekly Contest 286相关的知识,希望对你有一定的参考价值。

1. 题目一

给出题目一的试题链接如下:

1. 解题思路

这一题我的思路还是比较暴力的,要做的其实就是数值的检索,因此我们首先创建两个hash表来进行数值存储,这样检索的时间复杂度就是 O ( 1 ) O(1) O(1)了。

2. 代码实现

给出python代码实现如下:

class Solution:
    def findDifference(self, nums1: List[int], nums2: List[int]) -> List[List[int]]:
        s1, s2 = set(nums1), set(nums2)
        return [[x for x in s1 if x not in s2], [x for x in s2 if x not in s1]]

提交代码评测得到:耗时304ms,占用内存14.2MB。

2. 题目二

给出题目二的试题链接如下:

1. 解题思路

这一题直接使用greedy的方法即可。

对于每一个不符合条件的数字,只需要向后遍历然后找到下一个合适的数据进行保留即可,中间的数据都是重复数据,删除即可,在任何情况下都不可能被保留。

由此,遍历一遍即可得到最终的结果。

2. 代码实现

给出python代码实现如下:

class Solution:
    def minDeletion(self, nums: List[int]) -> int:
        cnt = 0
        i, n = 0, len(nums)
        while i < n:
            j = i+1
            while j < n and nums[i] == nums[j]:
                j += 1
            if j < n:
                cnt += 2
            i = j+1
        return n - cnt

提交代码评测得到:耗时1478ms,占用内存28.5MB。

3. 题目三

给出题目三的试题链接如下:

1. 解题思路

这一题我最开始的思路是直接把长度为k的回文数字全部求出来,不过这种思路遇到了超时,因此,我们的思路就修正为每次求取出某一个位置下的回文数字。

而求取得方式的话我们采用递归的方法,只要找到每个长度上面有的回文的数目即可。

2. 代码实现

给出python代码实现如下:

class Solution:
    def kthPalindrome(self, queries: List[int], intLength: int) -> List[int]:
        
        @lru_cache(None)
        def fn(n, middle):
            # print(n, middle)
            if n == 0:
                return 0
            if n <= 2:
                return 10 if middle else 9
            return 10 * fn(n-2, True) if middle else 9 * fn(n-2, True)
        
        @lru_cache(None)
        def query(idx, n, middle):
            if idx >= fn(n, middle):
                return -1
            elif n == 1:
                return idx if middle else idx+1
            elif n == 2:
                return 11*idx if middle else 11*(idx+1)
            
            k = idx // fn(n-2, True)
            r = idx % fn(n-2, True)
            k = k if middle else k+1
            return k*(10**(n-1)) + 10 * query(r, n-2, True) + k
        
        return [query(q-1, intLength, False) for q in queries]

提交代码评测得到:耗时1989ms,占用内存125.7MB。

3. 优化方案

后续看了一下别人的解法,还有一种更加直接的求第k大的数字的方法就是对于长度为n的回文数字,第k大的数字就是长度为(n+1)//2的数字当中第k大的数字构成的回文。

由此,就不需要做什么递归了,直接就能获得第k大的数字。

这样的话,方法也会更加优雅一些。

不过这里就不给出code了,有兴趣的读者可以自己实现一下。

4. 题目四

给出题目四的试题链接如下:

1. 解题思路

这一题我们的思路同样非常暴力,就是一个迭代算法就是了,使用cache来用空间换了时间的复杂度,感觉倒是反而没啥好讲的了。

2. 代码实现

给出python代码实现如下:

class Solution:
    def maxValueOfCoins(self, piles: List[List[int]], k: int) -> int:
        n= len(piles)
        
        @lru_cache(None)
        def dp(idx, k):
            if k == 0:
                return 0
            if idx == n-1:
                return sum(piles[idx][:k])
            cnt = 0
            res = dp(idx+1, k)
            for i, m in enumerate(piles[idx]):
                if i >= k:
                    break
                cnt += m
                res = max(res, cnt + dp(idx+1, k-i-1))
            return res
        
        return dp(0, k)

提交代码评测得到:耗时8825ms,占用内存130.4MB。

以上是关于LeetCode笔记:Weekly Contest 286的主要内容,如果未能解决你的问题,请参考以下文章

LeetCode笔记:Weekly Contest 317

LeetCode笔记:Weekly Contest 288

LeetCode笔记:Weekly Contest 299

LeetCode笔记:Weekly Contest 307

LeetCode笔记:Weekly Contest 325

LeetCode笔记:Weekly Contest 314