代码题(20)— 最长连续序列

1、128. 最长连续序列

给定一个未排序的整数数组,找出最长连续序列的长度。

要求算法的时间复杂度为 O(n)

示例:

输入: [100, 4, 200, 1, 3, 2]
输出: 4
解释: 最长连续序列是 [1, 2, 3, 4]。它的长度为 4。

方法1:
这道题要求求最长连续序列,并给定了O(n)复杂度限制,我们的思路是,使用一个集合set存入所有的数字,
然后遍历数组中的每个数字,如果其在集合中存在,那么将其移除,
然后分别用两个变量pre和next算出其前一个数跟后一个数,然后在集合中循环查找,
如果pre在集合中,那么将pre移除集合,然后pre再自减1,
直至pre不在集合之中,对next采用同样的方法,那么next-pre-1就是当前数字的最长连续序列,更新res。

class Solution {
public:
    int longestConsecutive(vector<int>& nums) {
        if(nums.empty())
            return 0;
        int res = 0;
        unordered_set<int> s(nums.begin(), nums.end());
        for(int i=0;i<nums.size();++i)
        {
            if(!s.count(nums[i]))
                continue;
            s.erase(nums[i]);
            int pre = nums[i] - 1;
            int next = nums[i] + 1;
            while(s.count(pre))
                s.erase(pre--);
            while(s.count(next))
                s.erase(next++);
            res = max(res, next-pre-1);
        }
        return res;
    }
};

方法2:

  我们也可以采用哈希表来做,刚开始哈希表为空,然后遍历所有数字,如果该数字不在哈希表中,那么我们分别看其左右两个数字是否在哈希表中,如果在,则返回其哈希表中映射值,若不在,则返回0,然后我们将left+right+1作为当前数字的映射,并更新res结果,然后更新d-left和d-right的映射值

class Solution {
public:
    int longestConsecutive(vector<int>& nums) {
        if(nums.empty())
            return 0;
        int res = 0;
        unordered_map<int, int> m;
        for(int val : nums)
        {
            if(m.count(val))
                continue;
            int left = m.count(val-1) ? m[val-1] : 0;
            int right = m.count(val+1) ? m[val+1] : 0;
            int sum = left + right +1;
            m[val] = sum;
            res = max(res, sum);
            m[val-left] = sum;
            m[val+right] = sum;
            
        }
        return res;
    }
};

猜你喜欢

转载自www.cnblogs.com/eilearn/p/9349247.html