lintcode---滑动窗口内唯一元素数量和 (Sliding Window Unique Elements Sum)
2017-12-09 14:59
513 查看
题目描述:
给一个数组和一个滑动窗口的大小, 求每一个窗口内唯一元素的个数和
样例:
给一个数组 nums = [1, 2, 1, 3, 3] 和 k = 3
第一个窗口为 [1, 2, 1], 只有 2 是唯一的, 计数为 1.
第二个窗口为 [2, 1, 3], 所有的元素都是唯一的, 计数为 3.
第三个窗口为 [1, 3, 3], 只有 1 是唯一的, 计数为 1.
总数为 1 + 3 + 1 = 5
返回 5
标签:
数组
思路讲解:这道题的就是将一个数组分成连续的若干个子数组(子数组间有重叠),重点就是求每一个子数组中唯一元素的个数。
一开始我的做法是暴力破解,即对每一个子数组进行排序,然后挑出没有重复的元素,然后将他们的和加在一起,显然这样的肯定是时间按不够的。
然后我对算法进行分析,发现在以第一次的基础上,下一个子数组,我们可以借助上一个子数组的结果,由于下一个子数组只是上一个子数组加上一个元素以及减去其最前面的元素。我们只需要对这两个元素与原子数组进行比较,就可以得到下一个子数组的唯一元素个数(具体比较看代码)。
给一个数组和一个滑动窗口的大小, 求每一个窗口内唯一元素的个数和
样例:
给一个数组 nums = [1, 2, 1, 3, 3] 和 k = 3
第一个窗口为 [1, 2, 1], 只有 2 是唯一的, 计数为 1.
第二个窗口为 [2, 1, 3], 所有的元素都是唯一的, 计数为 3.
第三个窗口为 [1, 3, 3], 只有 1 是唯一的, 计数为 1.
总数为 1 + 3 + 1 = 5
返回 5
标签:
数组
思路讲解:这道题的就是将一个数组分成连续的若干个子数组(子数组间有重叠),重点就是求每一个子数组中唯一元素的个数。
一开始我的做法是暴力破解,即对每一个子数组进行排序,然后挑出没有重复的元素,然后将他们的和加在一起,显然这样的肯定是时间按不够的。
然后我对算法进行分析,发现在以第一次的基础上,下一个子数组,我们可以借助上一个子数组的结果,由于下一个子数组只是上一个子数组加上一个元素以及减去其最前面的元素。我们只需要对这两个元素与原子数组进行比较,就可以得到下一个子数组的唯一元素个数(具体比较看代码)。
class Solution { public: /* * @param : the given array * @param : the window size * @return: the sum of the count of unique elements in each window */ int slidingWindowUniqueElementsSum(vector<int> nums, int k) { // write your code here int length=nums.size(); vector<int> temp; int res=0; if(k>length){//当窗口的长度大于数组的长度时,直接对数组找唯一元素个数 sort(nums.begin(),nums.end()); int flag=0; for(int j=0;j<length-1;j++) { if(nums[j]!=nums[j+1]&&flag==0){ res++; }else if(nums[j]!=nums[j+1]&&flag==1){ flag=0; }else{ flag=1; } } if(flag==0){ res++; } return res; } int *p=new int[length-k+1];//用来存储每一个子数组唯一元素的个数 for(int i=0;i<length-k+1;i++) { if(i==0){//第一个子数组的唯一元素个数的计算 for(int j=0;j<k;j++) { temp.push_back(nums[j+i]); } sort(temp.begin(),temp.end()); int flag=0; for(int j=0;j<k-1;j++) { if(temp[j]!=temp[j+1]&&flag==0){ res++; }else if(temp[j]!=temp[j+1]&&flag==1){ flag=0; }else{ flag=1; } } if(flag==0){ res++; } p[i]=res; }else{ if(nums[i-1]==nums[i+k-1]){//首先判断删除的元素和新增加的元素是否相同,如果相同,则说明该子数组与上一个数组一样,即唯一元素个数也一样。 p[i]=p[i-1]; }else{ int flag1=0;//存储上一个子数组的最前面的元素在后面元素出现的个数 int flag2=0;//新加入的元素在子数组去除第一个元素中出现的个数 for(int j=0;j<k-1;j++) { if(nums[i-1]==nums[i+j]){ flag1++; }else if(nums[i+k-1]==nums[i+j]){ flag2++; } } if(flag1==1){//根据flag去判断在上一个子数组的基础上是加一还是减一这样的操作 p[i]=p[i-1]+1; }else if(flag1==0){ p[i]=p[i-1]-1; }else{ p[i]=p[i-1]; } if(flag2==0){ p[i]=p[i]+1; }else if(flag2==1){ p[i]=p[i]-1; } } } } return sumarray(p,length-k+1); } int sumarray(int *p,int length) { int res=0; for(int i=0;i<length;i++) { cout<<p[i]<<" "; res=res+p[i]; } return res; } };
相关文章推荐
- LINTCODE——Sliding Window Unique Elements Sum
- lintcode:Sliding Window Maximum
- LintCode:H-Sliding Window Median
- 692. 滑动窗口内唯一元素数量和
- LintCode - Sliding Window Median
- 滑动窗口内唯一元素数量和-LintCode
- 滑动窗口内唯一元素数量和
- [Lintcode] Remove Linked List Elements 删除链表中的元素
- LintCode Sliding Window Matrix Maximum
- Lintcode 360 Sliding Window Median
- LintCode "Sliding Window Median" & "Data Stream Median"
- 239. Sliding Window Maximum&滑动窗口的最大值
- LintCode UniquePaths 不同的路径
- LintCode Majority Number 主元素
- lintcode: Partition Equal Subset Sum
- lintcode 中等题:minimum window substring 最小子串覆盖
- Lintcode: k Sum II
- LintCode-Java-172-删除元素
- sliding window 滑动窗口(单调队列)
- LeetCode Sliding Window Maximum 滑动窗口(双向链表实现队列效果)