题目

题目来源:力扣(LeetCode)

给定两个排序后的数组 A 和 B,其中 A 的末端有足够的缓冲空间容纳 B。 编写一个方法,将 B 合并入 A 并排序。
初始化 A 和 B 的元素数量分别为 m 和 n。

示例:

输入:
A = [1,2,3,0,0,0], m = 3
B = [2,5,6], n = 3

输出: [1,2,2,3,5,6]

思路分析

逆向双指针
因为 A 中的数字都集中在前 m - 1 的位置,所以 A 的空间都集中在后面,所以从后向前处理排序的数据会更好,能够节省空间。
A 和 B 都从后往前进行遍历(每次选两者中较大值,不会将 A 中原有元素覆盖掉)

  1. var merge = function (A, m, B, n) {
  2. // 定义两个指针
  3. let pa = m - 1, pb = n - 1;
  4. // 定义一个总长度,合并到链表上的长度
  5. let tail = m + n - 1;
  6. // 定义合并后的数组
  7. var cur;
  8. // 只要两个有一个大于0.证明还能合并
  9. while (pa >= 0 || pb >= 0) {
  10. if (pa === -1) {
  11. cur = B[pb--];
  12. } else if (pa === -1) {//pa合并完了,合并pb
  13. cur = A[pb--];
  14. } else if (pb === -1) {//pb合并完了,合并pa
  15. cur = A[pa--];
  16. } else if (A[pa] > B[pb]) {//如果两个数组都没有合并完,看哪个数组大;如果a数组比b数组大,合并pa
  17. cur = A[pa--];
  18. } else {//最后一组就合并pb数组
  19. cur = B[pb--];
  20. }
  21. //将cur存到a上面倒着去合并,这样所有的值都合并到A上面了
  22. A[tail--] = cur;
  23. }
  24. };