First Missing Positive解题报告

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/jining11/article/details/82726492

其实看到这种hard类型的题目,还是有点紧张的,但有惊无险,一次就过了。

题目描述

Given an unsorted integer array, find the smallest missing positive integer.

大意就是说,给你一堆毫无规则的正数,你要给出其中不包含的正数里面最小的那一个。

额外建立数组法

一开始我其实想到了那个查找第K大元素的典型问题,但是排序似乎太浪费时间了,毕竟我们只是要检验一种存在性,而不是获得一种有序性,那么如何验证一个元素的存在呢,一个简单的方法是将数组里这个元素出现的位置置一,而把其他位置置为零。除此之外,由于数据的连续性特征,数组的大小只需设置为给出的元素的数目即可。

class Solution {
public:
    int firstMissingPositive(vector<int>& nums) { 
    	int * x = new int[nums.size()]();
    	for (int i = 0; i < nums.size(); i++) {
    		if (nums[i] > 0 && nums[i] <= nums.size()) {
    			x[nums[i]-1] = 1;
    		}
    	}
    	int result = nums.size()+1;
    	for (int i = 0; i < nums.size(); i++) {
    		if (!x[i]) {
    			result = i+1;
    			break;
    		}
    	}
    	delete [] x;
    	return result;
    }
};

临交的时候我才发现题目里面有这么一句话:

Your algorithm should run in O(n) time and uses constant extra space.

由于要新申请数组,所以我所需的额外空间是O(n)级别而非O(1)常量级。

试着交了一下,居然过了,但还是想试试有没有符合要求的解法。

就地修改交换法

既然所开辟新数组的大小恰恰与给出的元素一致,那为什么不在原来的基础上修改呢?

class Solution
{
public:
    int firstMissingPositive(vector<int>& nums) {
    	int n = nums.size();
        for(int i = 0; i < n; ++ i)
            while(nums[i] > 0 && nums[i] <= n && nums[nums[i] - 1] != nums[i])
                swap(nums[i], nums[nums[i] - 1]);
        
        for(int i = 0; i < n; ++ i)
            if(nums[i] != i + 1)
                return i + 1;
        
        return n + 1;
    }
};

猜你喜欢

转载自blog.csdn.net/jining11/article/details/82726492