题目

Given an unsorted array of integers, find the length of the longest consecutive elements sequence.

For example,

Given [100, 4, 200, 1, 3, 2],

The longest consecutive elements sequence is [1, 2, 3, 4]. Return its length: 4.

Your algorithm should run in O(n) complexity.

分析

给定一个整形数组,求出最长的连续序列。例如数组[100,4,200,1,3,2],最长的连续序列长度为[1,2,3,4],长度为4。要求时间复杂度为O(n)。

首先,想到的办法就是 排序—>得到最长连续长度;但是不符合要求的时间复杂度,所以不予采用。

其次,第二个方法是利用c++中的set,直接会排序,并且没有重合的,但是set背后实现的原理牵扯到红黑树,时间复杂度同样不满足。

所以,解决该问题还是应该从哈希入手,建立hash索引,把查找的元素周围的都访问个遍,求出个临时最大值跟全局最大值比较。当再次访问该段的元素的时候,直接跳过。这样保证时间复杂度为O(n)。

c++11中数据结构为unordered_set,保证查找元素的时间复杂度为O(1),但是奇怪的是我才用的unordered_set并没有通过,给出的结果是TLE,于是,我就改用了unordered_map最后通过测试。

AC代码

class Solution {
public:
//方法一:使用unordered_set
int longestConsecutive1(vector<int>& nums) {
if (nums.empty() || nums.size() == 1)
return nums.size(); //保存序列元素个数
int size = nums.size();
unordered_set<int> existNums, visitedNums;
for (int i = 0; i < size; ++i)
{
existNums.insert(nums[i]);
} int maxCount = 0;
for (int i = 0; i < size; ++i)
{
//每个连续序列中的元素只需要遍历一次,只有不在已遍历序列中时,向两侧探查
if (visitedNums.find(nums[i]) != visitedNums.end())
continue;
int count = 1, less = nums[i] - 1, great = nums[i] + 1;
while (existNums.find(less) != existNums.end())
{
visitedNums.insert(less);
++count;
--less;
}//while
while (existNums.find(great) != existNums.end())
{
visitedNums.insert(great);
++count;
--less;
}//while
if (count > maxCount)
maxCount = count;
}//for
return maxCount;
} //方法二:使用unordered_map
int longestConsecutive(vector<int>& nums) {
if (nums.empty() || nums.size() == 1)
return nums.size(); //保存序列元素个数
int size = nums.size();
unordered_map<int, bool> visitedNums;
for (int i = 0; i < size; ++i)
{
visitedNums[nums[i]] = false;
} int maxCount = 0;
for (int i = 0; i < size; ++i)
{
//若已访问过,则跳过
if (visitedNums[nums[i]])
continue;
int count = 1;
//改变访问标记
visitedNums[nums[i]] = true; int less = nums[i] - 1, great = nums[i] + 1;
while (visitedNums.find(less) != visitedNums.end())
{
visitedNums[less] = true;
--less;
++count;
}//while while (visitedNums.find(great) != visitedNums.end())
{
visitedNums[great] = true;
++great;
++count;
}//while
if (count > maxCount)
maxCount = count;
}//for
return maxCount;
} };

GitHub测试程序源码

最新文章

  1. Moon.Orm 常见查询实例
  2. Spark编译与打包
  3. 代理延迟加载中proxy和弄no-proxy区别
  4. Linux学习笔记(18) Shell编程之流程控制
  5. 弱键(Weak Key, ACM/ICPC Seoul 2004, UVa1618)
  6. 课堂Scrum站立会议演示
  7. Asp.net操作Excel(终极方法NPOI)(转)
  8. Elasticsearch学习笔记
  9. POJ 1862
  10. POI 操作Excel疑难点笔记
  11. nodeCZBK-笔记1
  12. maven 安装本地jar
  13. UWP简单测试
  14. clientdataset新增append新增多条记录的时候报错 key valation
  15. Spring autowire自动装配 ByType和ByName
  16. 学习 Spring (八) 注解之 Bean 的定义及作用域
  17. cocos开发学习记录
  18. linux查看磁盘大小df命令
  19. java 面试基础总结(二)---多线程
  20. jQuery UI练习

热门文章

  1. Batch梯度下降
  2. 漫谈Code Review的错误实践
  3. 超文本传输协议(HTTP)
  4. 前端HTML以及HTML5(基本标签)
  5. 关于ev||event事件对象的兼容写法
  6. Linux 网卡驱动的安装
  7. uvm_reg_fifo——寄存器模型(十五)
  8. 在一个另一个文件中 #include一个**dlg.h文件,会发生dlg的资源ID未定义的错误 :
  9. 多并发下 SimpleDateFormat 出现错误
  10. NBear简介与使用图解