寻找缺失的数

来源:互联网 发布:淘宝怎么联系店家 编辑:程序博客网 时间:2024/05/12 17:23

题目选自 lintcode


给出一个包含 0 .. N 中 N 个数的序列,找出0 .. N 中没有出现在序列中的那个数。
样例
N = 4 且序列为 [0, 1, 3] 时,缺失的数为2。
注意
可以改变序列中数的位置。
挑战
在数组上原地完成,使用O(1)的额外空间和O(N)的时间。

解法1:空间O(1),时间复杂度O(n)

首先将0 - N求和,依次减掉序列中的数,得到最终的数。

class Solution {public:    /**         * @param nums: a vector of integers     * @return: an integer     */    int findMissing(vector<int> &nums) {        // write your code here        int size = nums.size();        int missnum= size * (size + 1) / 2;        if(size == 0)            return 0;        for(int i = 0; i < size; i++)        {            missnum -= nums[i];        }        return missnum;    }};

问题:当序列很大时,会出现溢出问题,longlongint为2^64,要算1/2*N*(N+1),大约2^32时便超出范围,产生溢出。可以采用牺牲空间的方法,解决此问题。利用一张N+1的表,初始化为0,如序列中有的置为1,遍历一遍后,剩下为零的数即为所需。耗用空间为2^32/8/1024/1024/1024 = 0.5 GB。

解法2:空间O(n+1),时间O(n)

开辟N个元素的数组,初始化为0,利用序列中的数据作为索引,对应数组位置置1,遍历一遍0所在的位置就是要找的数。

class Solution {public:    /**         * @param nums: a vector of integers     * @return: an integer     */    int findMissing(vector<int> &nums)    {        // write your code here        int size = nums.size();        int missnum = 0;        vector <bool> listall(size+1);         if(size == 0)            return 0;        for(auto pd = nums.begin(); pd != nums.end(); pd++)        {            listall[*pd] = 1;        }        for(auto p = listall.begin(); p != listall.end(); p++)        {            if(*p == 0)            {                      missnum = p - listall.begin();                break;               }         }        return missnum;    }};

问题

以上两种方法只适用于给定数组只有正整数,并且不重复出现,若出现以上问题,就会需要修改以上算法,使得算法更具普适性。

class Solution {public:    /**         * @param A: a vector of integers     * @return: an integer     */    int firstMissingPositive(vector<int> A) {        // write your code here        sort(A.begin(), A.end(),less<int>());        int size_A = A.size();        if(size_A == 0)            return 1;        int fast = 1;        int slow = 1;        int temp = A[0];        int newSize = 0;        for(int j = 0; j < size_A; j++)        {            if(temp != A[fast])            {                A[slow] = A[fast];                slow++;                newSize++;                temp = A[slow - 1];            }            fast++;        }        int result = 0;        int count = 0;        int i;        for(i = 0; i < newSize; i++)        {            if(A[i] <= 0)            {                count++;                continue;            }            if(A[i] != (i - count + 1))            {                break;            }        }        return (i - count + 1);    }};

在此输入正文

0 0