leecode学习记录7——88.合并有序数组

leecode学习记录七

合并有序数组

难度:简单

给定两个有序整数数组 nums1 和 nums2,将 nums2 合并到 nums1 中,使得 num1 成为一个有序数组。

说明:

初始化 nums1 和 nums2 的元素数量分别为 m 和 n。
你可以假设 nums1 有足够的空间(空间大小大于或等于 m + n)来保存 nums2 中的元素。
示例:

输入:
nums1 = [1,2,3,0,0,0], m = 3
nums2 = [2,5,6], n = 3

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

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/merge-sorted-array
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

解题思路

1.从头开始有两个数组两个指针p、q,指向要比较的元素,还有一个数组作为目标数值向内插入数值,有一指针i
2.先将数组合并在进行排序,代码量少,但时间复杂度较高 (没想到的做法)
3.指针从尾开始,用两数组用p,q指向最后一个元素,找最大的插入,从nums1的尾部开始插入,本题最适合的方法,不需要再声明一个数组,时间复杂度O(m+n),空间复杂度O(1) (没想到的做法)

代码

//方法一 我自己的实现方法,代码不咋优美
class Solution {
    public void merge(int[] nums1, int m, int[] nums2, int n) {
        int p = 0 , q = 0 , i = 0;
        int[] temp = new int[m+n];
        while((p < m) && (q < n)){
            if(nums1[p] <= nums2[q]){
                temp[i++] = nums1[p++];
            }
            else{
                temp[i++] = nums2[q++];
            }
        }
        //arraycopy(arr1,p,arr2,q,num);arr1为要复制的数组,p为复制的初始位置,arr2为要复制到的目标数组,q为初始位置,num为复制的个数
        if (p < m)
            System.arraycopy(nums1, p, temp, i, m - p);
        if (q < n)
            System.arraycopy(nums2, q, temp, i, n - q);
        System.arraycopy(temp, 0, nums1, 0, m+n);
    }
}

//方法一 题解的代码,代码比上面的简洁,思路一样,空间复杂度稍微低一些
class Solution {
  public void merge(int[] nums1, int m, int[] nums2, int n) {
    // Make a copy of nums1.
    int [] nums1_copy = new int[m];
    System.arraycopy(nums1, 0, nums1_copy, 0, m);

    // Two get pointers for nums1_copy and nums2.
    int p1 = 0;
    int p2 = 0;

    // Set pointer for nums1
    int p = 0;

    // Compare elements from nums1_copy and nums2
    // and add the smallest one into nums1.
    while ((p1 < m) && (p2 < n))
      nums1[p++] = (nums1_copy[p1] < nums2[p2]) ? nums1_copy[p1++] : nums2[p2++];

    // if there are still elements to add
    if (p1 < m)
      System.arraycopy(nums1_copy, p1, nums1, p1 + p2, m + n - p1 - p2);
    if (p2 < n)
      System.arraycopy(nums2, p2, nums1, p1 + p2, m + n - p1 - p2);
  }
}

//方法二 合并数组再排序
class Solution {
  public void merge(int[] nums1, int m, int[] nums2, int n) {
    System.arraycopy(nums2, 0, nums1, m, n);
    Arrays.sort(nums1);
  }
}

//方法三
class Solution {
  public void merge(int[] nums1, int m, int[] nums2, int n) {
    // two get pointers for nums1 and nums2
    int p1 = m - 1;
    int p2 = n - 1;
    // set pointer for nums1
    int p = m + n - 1;

    // while there are still elements to compare
    while ((p1 >= 0) && (p2 >= 0))
      // compare two elements from nums1 and nums2 
      // and add the largest one in nums1 
      nums1[p--] = (nums1[p1] < nums2[p2]) ? nums2[p2--] : nums1[p1--];

    // add missing elements from nums2
    System.arraycopy(nums2, 0, nums1, 0, p2 + 1);
  }
}

总结

1.有从尾开始的意识,前面一些题也有一些从尾开始或首位一起开始的做法,可能会更加简单;
2.条件 ? 表达式1 : 表达式2,这个式子可使代码更加简洁
3.arraycopy(arr1,p,arr2,q,num);arr1为要复制的数组,p为复制的初始位置,arr2为要复制到的目标数组,q为初始位置,num为复制的个数

发布了11 篇原创文章 · 获赞 0 · 访问量 57

猜你喜欢

转载自blog.csdn.net/yqzsszl/article/details/103835903