LeetCode编程题-----数组|88、268、283题解及优化

88.合并两个有序数组

在这里插入图片描述
1.读题后发现,

  • 这题引导着你在数组1中排序(把数组2加进去后)(当然数组加入也可用System.arraycopy(nums2, 0, nums1,m,n);)
  • 所以取了个巧,直接排序
// 击败35%
 public void merge(int[] nums1, int m, int[] nums2, int n) {
  	for (int i = m; i < m + n; i++) {
   		nums1[i] = nums2[i - m];
  	}
    Arrays.sort(nums1);
    for (int i : nums1) {
   		System.out.println(i);
    }
 }

2.尝试想过插入排序(复杂度高不再罗列)

  • 直接将数组2中的逐个数字直接插入指定位置
  • 后来考虑不仅要遍历判断找出插入索引,也要逐个位移怕复杂度过高

3.通过双指针交替移动

  • 定义两个变量比较麻烦,直接倒着赋值
  • 用mn作为索引变量由大到小比较后赋值
  • 赋值后移动指针
  • 注意
  • 1.开始时mn都要减一,因为索引是从0开始的
  • 2.要考虑一个数组遍历完而另一个数组没有遍历完的情况,分别对应if中的和else中的
//100%
public void merge(int[] nums1, int m, int[] nums2, int n) {
	int i = m + n - 1;
	m--;
	n--;
	for (; n >= 0 ; i--) {
		if (m >= 0&& nums1[m] > nums2[n]) {
			nums1[i] = nums1[m--];
		} else 
			nums1[i] = nums2[n--];
	}for (int j : nums1) {
		System.out.println(j + " ");
	}
}

268.缺失数字

在这里插入图片描述
1.读题后容易想到

  • 缺失一个数那么就相当于再定义一个数组,存放它该有的数,然后两数组逐一比较
  • 而定义的新数组中存放的是顺序的,故可以直接用变量递增表示
  • 需要考虑的特殊情况是:
  • 1.定义的变量i的范围为0 - length-1,否则会空指针异常
  • 2.既然如此我们就要考虑如果缺失的是最大的数(最后一个数)的情况,可直接返回i(i此时已经+1)
//22%
	public int missingNumber(int[] nums) {
		Arrays.sort(nums);
        int i = 0;
		for (; i < nums.length; i++)
			if (nums[i] != i)return i;
        return i;
	}

2.做完后借鉴优秀做法发现:求和公式

  • 原本的数组之和 - 传入的缺失的数组之和 = 缺失的数字
  • 简直精辟,可见数学知识的实际运用也是相当的重要
//99%
	public int missingNumber(int[] nums) {
		int sum = nums.length*(nums.length+1)/2;
		System.out.println(sum);
		int sum1 = 0;
		for(int i:nums) {
			sum1 += i;
		}
		return sum-sum1;
	}

283.移动零

在这里插入图片描述 1.读完题容易想到

  • 类似插入排序将0元素遍历找出插入到最后,其他元素前移,同时n–
  • 因为后面的是0,已经归位,就不用遍历
  • 这样分析,它在查找0时遍历一次,找到后又要逐个移位,复杂度为O(n^2),有没有更优解呢
//12%
	public void moveZeroes(int[] nums) {
		int n = nums.length;
		for(int i = 0;i<n;) {
			if(nums[i] == 0) {
				for(int j = i;j<nums.length-1;j++) {
					nums[j] = nums[j+1];
				}
				nums[nums.length-1] = 0;
				n--;
			}
			else {
				i++;
			}
		}
	}

2.这种移动问题大多可以用双指针交换来完成

  • 两指针从0开始往后移动,遇到0就不移动标记指针,不是0就交换
  • 所以0会被标记指针交换位置指针从而完成交换,将0逐步移动到最后
  • 遇到这种移动的问题,如果不是过于复杂就先不用考虑插入,遍历和插入遍历的过程复杂度较高,可以尝试双指针交换或蠕虫思想来解决问题
public void moveZeroes(int[] nums) {
	        int zeroPos = 0;
	        for (int i = 0; i < nums.length; i++) {
	            if (nums[i] != 0) {
	                int tmp = nums[zeroPos];
	                nums[zeroPos] = nums[i];
	                nums[i] = tmp;
	                zeroPos++;
	            }
	        }
	    }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值