leetcode_321. 拼接最大数

举报
悲恋花丶无心之人 发表于 2021/02/03 01:00:24 2021/02/03
【摘要】 目录 一、题目内容 二、解题思路 三、代码 一、题目内容 给定长度分别为 m 和 n 的两个数组,其元素由 0-9 构成,表示两个自然数各位上的数字。现在从这两个数组中选出 k (k <= m + n) 个数字拼接成一个新的数,要求从同一个数组中取出的数字保持其在原数组中的相对顺序。...

目录

一、题目内容

二、解题思路

三、代码


一、题目内容

给定长度分别为 m 和 n 的两个数组,其元素由 0-9 构成,表示两个自然数各位上的数字。现在从这两个数组中选出 k (k <= m + n) 个数字拼接成一个新的数,要求从同一个数组中取出的数字保持其在原数组中的相对顺序。

求满足该条件的最大数。结果返回一个表示该最大数的长度为 k 的数组。

说明: 请尽可能地优化你算法的时间和空间复杂度。

示例 1:

输入:
nums1 = [3, 4, 6, 5]
nums2 = [9, 1, 2, 5, 8, 3]
k = 5
输出:
[9, 8, 6, 5, 3]

示例 2:

输入:
nums1 = [6, 7]
nums2 = [6, 0, 4]
k = 5
输出:
[6, 7, 6, 0, 4]

示例 3:

输入:
nums1 = [3, 9]
nums2 = [8, 9]
k = 3
输出:
[9, 8, 9]

二、解题思路

题目太难,总之就是遍历所有的组合k=i+j,然后融合两个数组,比较每次res的大小,得到最大的。

三、代码


  
  1. class Solution1:
  2. def maxNumber(self, nums1: list, nums2: list, k: int) -> list:
  3. m = len(nums1)
  4. n = len(nums2)
  5. res = [0 for _ in range(k)]
  6. for i in range(max(0, k - n), k + 1):
  7. if i <= m:
  8. arr = self.merge(nums1=self.maxlist(nums1, i),
  9. nums2=self.maxlist(nums2, k - i),
  10. k=k)
  11. if self.compare_same_location_num(arr, 0, res, 0):
  12. res = arr
  13. return res
  14. def maxlist(self, nums, k):
  15. n = len(nums)
  16. res = [0 for _ in range(k)]
  17. j = 0
  18. for i in range(n):
  19. while n - i + j > k and j > 0 and nums[i] > res[j - 1]:
  20. j -= 1
  21. if j < k:
  22. res[j] = nums[i]
  23. j += 1
  24. return res
  25. def merge(self, nums1, nums2, k):
  26. res = [0 for _ in range(k)]
  27. i, j = 0, 0
  28. for r in range(k):
  29. if self.compare_same_location_num(nums1, i, nums2, j):
  30. res[r] = nums1[i]
  31. i += 1
  32. else:
  33. res[r] = nums2[j]
  34. j += 1
  35. return res
  36. def compare_same_location_num(self, nums1, i, nums2, j):
  37. while i < len(nums1) and j < len(nums2) and nums1[i] == nums2[j]:
  38. i += 1
  39. j += 1
  40. return j == len(nums2) or (i < len(nums1) and nums1[i] > nums2[j])
  41. class Solution2:
  42. def maxNumber(self, nums1: list, nums2: list, k: int) -> list:
  43. # 求出单个数组可以组成i位的最大数组
  44. def getMaXArr(nums, i):
  45. if not i:
  46. return []
  47. # pop表示最多可以不要nums里几个数字,要不组成不了i位数字
  48. stack, pop = [], len(nums) - i
  49. for num in nums:
  50. while pop and stack and stack[-1] < num:
  51. pop -= 1
  52. stack.pop()
  53. stack.append(num)
  54. return stack[:i]
  55. def merge(tmp1, tmp2):
  56. return [max(tmp1, tmp2).pop(0) for _ in range(k)]
  57. res = [0] * k
  58. for i in range(k + 1):
  59. if i <= len(nums1) and k - i <= len(nums2):
  60. # 取num1的i位, num2的k - i
  61. tmp1 = getMaXArr(nums1, i)
  62. tmp2 = getMaXArr(nums2, k - i)
  63. # 合并
  64. tmp = merge(tmp1, tmp2)
  65. if res < tmp:
  66. res = tmp
  67. return res
  68. if __name__ == '__main__':
  69. nums1 = [3, 4, 6, 5]
  70. nums2 = [9, 1, 2, 5, 8, 3]
  71. k = 5
  72. s1 = Solution1()
  73. ans1 = s1.maxNumber(nums1, nums2, k)
  74. print(ans1)
  75. s2 = Solution2()
  76. ans2 = s2.maxNumber(nums1, nums2, k)
  77. print(ans2)

文章来源: nickhuang1996.blog.csdn.net,作者:悲恋花丶无心之人,版权归原作者所有,如需转载,请联系作者。

原文链接:nickhuang1996.blog.csdn.net/article/details/110470551

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。