1.题目描述
2.代码
思想:对每一个可能的序列都创建一个容器保存起来,记录它的序列尾,每次查询可匹配的队列尾部,优先匹配那些当前序列长度小于3的序列。比如:对于待拆分的 1233445 ,会生产这样的序列 123 和 3 ,当
4 到来时,优先匹配 3 (请思考为什么要这样?),这样,遍历结束后,如果有哪一个序列的长度是小于3的,说明不存在这样的拆分。
优化:而实际上我们并不需要维护这样的一些序列,从上面分析看出,我们注重的信息只是序列的尾元素n 及其长度 size ,所以,对每个序列,我们需要维护的仅此两个变量。
实现:通过使用尾元素作为 key 的map容器 backs ,小顶堆的优先队列,则 backs[key] 记录序列尾元素值为 key 的所有序列的长度,以同样元素结尾的不停长度的(序列)就这样被维护在一个 vector ,且长度较小的放在优先队列的头部,匹配的时候优先出列。再者,维护一个当前有多少序列的长度小于3的变量 SquenceSizeLess3 ,最终依靠这样变量判断是否拆分成功。
class Solution {
public:
bool isPossible(vector<int>& nums) {
//小顶堆,小的元素作为队列头
unordered_map<int, priority_queue<int, vector<int>, std::greater<int>>> backs;
//记录有多少个squence的长度小于3
int SquenceSizeLess3 = 0;
for(int num : nums) {
if(!backs[num - 1].empty()) {
int size = backs[num - 1].top();
backs[num - 1].pop();
backs[num].push(++size);
if(size == 3)
SquenceSizeLess3--;
} else {
//找不到可匹配的队尾,创建新的squence
backs[num].push(1);
SquenceSizeLess3++;
}
}
return SquenceSizeLess3 == 0;
}
};
参考:leetcoe上的discussion
联系邮箱:sysuygm@163.com