LeetCode-268:Missing Number(寻找缺失数字)

来源:互联网 发布:linux 线程等待 编辑:程序博客网 时间:2024/06/03 08:52

Question

Given an array containing n distinct numbers taken from 0, 1, 2, …, n, find the one that is missing from the array.

For example:

Given nums = [0, 1, 3] return 2.

Note:

Your algorithm should run in linear runtime complexity. Could you implement it using only constant extra space complexity?

Idea

给定一个含有n个不重复数字的数组,n个数字来自0, 1, 2, …, n, 找出其中丢失的数字。(这里并没有说明是按序排列的数组)

  1. Xor异或:由于b^b=0(这里是进行位异或),所以a^b^b=a^0=a.

    • 这里取a=0,依次与‘i’,‘nums[i]’进行异或运算.
    • 如:a = a^0^0^1^1…^k^…n^n = a^k = 0^k = k.
  2. Sum求和:由于题目告诉只缺少一个数字,故用0~n的和减去数组的和得到的即为要求的数字.

    • 0~n的和:n(n+1)/2.
  3. BinarySearch:将数组进行排序后,可以利用二分查找的方法来找到缺少的数字,不过对算法进行略微的改动.

Code

Xor异或—Java

public class Solution {    public int missingNumber(int[] nums) {        int a = 0, i = 0;        for (i=0; i<nums.length;i++){            a = a^i^nums[i];        }        return a^i;    }}
* 算法中i从0~n-1(因为数组的大小为n),所以在循环结束后,i<=nums[i];* 如果缺少的数字k<n,则最后a^i以消去最后的nums[n-1];* 如果缺少的数字k=n,则最后a^i=i,刚好为缺少的数字n;* 所以最后返回的值为a^i,这里注意i要设置为for循环外的变量。* 时间复杂度低,Runtime:1ms.

Sum求和—Java

public class Solution {    public int missingNumber(int[] nums) {        int n = nums.length;        int sum = (n+0)*(n+1)/2;        for (int i=0; i<n; i++){            sum -= nums[i];        }        return sum;    }}
  • 算法的时间复杂度为O(n),空间复杂度为O(1)
  • Runtime:1ms.

BinarySearch—Java

public class Solution {    public int missingNumber(int[] nums) {        Arrays.sort(nums);        int low = 0;        int high = nums.length;        while (low < high){            int mid = (low+high)/2;            if (nums[mid] > mid) high = mid;            else low = mid+1;        }        return low;    }}
  • 算法这里有部分的变动,需要注意:
    • high = nums.length,而不是nums.length-1,这里相当于high = n,因为搜索范围为0~n;
    • 循环条件为low<high,而不是low<=high
  • 算法的时间复杂度较前两个要高
原创粉丝点击