当前位置:   article > 正文

代码随想录算法训练营 DAY7 | 哈希专题

代码随想录算法训练营 DAY7 | 哈希专题

 leetcode 四数之和https://leetcode.cn/problems/4sum-ii/submissions/

  1. class Solution {
  2. public:
  3. int fourSumCount(vector<int>& nums1, vector<int>& nums2, vector<int>& nums3, vector<int>& nums4) {
  4. unordered_map<int,int> map1;
  5. unordered_map<int,int> map2;
  6. int size=nums1.size();
  7. int ans=0;
  8. for(int i=0;i<size;i++){
  9. for(int j=0;j<size;j++){
  10. map1[nums1[i]+nums2[j]]++;
  11. }
  12. }
  13. for(int i=0;i<size;i++){
  14. for(int j=0;j<size;j++){
  15. map2[nums3[i]+nums4[j]]++;
  16. }
  17. }
  18. for(auto it1=map1.begin();it1!=map1.end();it1++){
  19. for(auto it2=map2.begin();it2!=map2.end();it2++){
  20. if(it1->first + it2->first==0){
  21. ans+=it1->second * it2->second;
  22. }
  23. }
  24. }
  25. return ans;
  26. }
  27. };

解析: 利用hashmap当中间储存器,分别把前两段的和,和后两段的和统计出来,再遍历两个hashmap来确定四数之和。以空间换时间,要么一个数只是要匹配四层循环。

leetcode 赎金信https://leetcode.cn/problems/ransom-note/submissions/

  1. class Solution {
  2. public:
  3. bool canConstruct(string ransomNote, string magazine) {
  4. unordered_map<int,int> map;
  5. for(int i=0;i<ransomNote.size();i++){
  6. map[ransomNote[i]]++;
  7. }
  8. for(int i=0;i<magazine.size();i++){
  9. map[magazine[i]]--;
  10. }
  11. for(auto it=map.begin();it!=map.end();it++){
  12. if(it->second>0){
  13. return false;
  14. }
  15. }
  16. return true;
  17. }
  18. };

解析: 其实这道题和leetcode 242 一样的,本质思想都是分门别类把,还是桶思想,把相同的属性放在一个桶里面,没什么特别之处。

 leetcode 三数之和icon-default.png?t=MBR7https://leetcode.cn/problems/3sum/submissions/

  1. class Solution {
  2. public:
  3. vector<vector<int>> threeSum(vector<int>& nums) {
  4. vector<vector<int>> ans;
  5. sort(nums.begin(),nums.end());
  6. for(int i=0;i<nums.size();i++){
  7. if (nums[i] > 0) {
  8. return ans;
  9. }
  10. if(i>0&& nums[i]==nums[i-1]){
  11. continue;
  12. }
  13. int left = i+1;
  14. int right= nums.size()-1;
  15. while(left<right){
  16. if(nums[i] + nums[left] + nums[right]>0){
  17. right--;
  18. }else if(nums[i] + nums[left] + nums[right]<0){
  19. left++;
  20. }else{
  21. ans.push_back({nums[i],nums[left],nums[right]});
  22. while (right > left && nums[right] == nums[right - 1]) right--;
  23. while (right > left && nums[left] == nums[left + 1]) left++;
  24. left++;
  25. right--;
  26. }
  27. }
  28. }
  29. return ans;
  30. }
  31. };

解析:这道题真的是让我绷不住了,刚开始的没有一点思路,不知道从何开始筛选寻找这三个数。

接着就是想到暴力算法,三层for循环vector直接收集所有的答案,最后hashmap去重。然后想你三层for循环能干的事情,我hashset以空间换时间两层for循环给你搞定。结果,我擦,怎么去重?,通常的hashset以空间换时间,最多是统计次数。收集所有不重复的结果。去重是真的复杂。

难道,难道我只能使用最后的必杀技了嘛,我从脑海深处,慢慢拔出双指针这把利剑,双指针?巧妙的使用两个指针,在数组间移动,竟然能达到减少多层for循环的效果。我该怎么用??!!,啊啊,要长出脑子了。。。

冥冥之中,有个声音在脑海中回荡。。。

双指针搭配排序才能发挥出巨大的威力,双指针的根本在于,利用顺序,对比,不断的移动,扩张,收缩。

我懂了,以雷霆击碎黑暗!! i为第一层for遍历, left, right 指针,分别为i+1 ,length-1。第一层i是地毯式搜索,left 和right 区间内寻找正确答案。

leetccode 四数之和icon-default.png?t=MBR7https://leetcode.cn/problems/4sum/

  1. class Solution {
  2. public:
  3. vector<vector<int>> fourSum(vector<int>& nums, int target) {
  4. vector<vector<int>> result;
  5. sort(nums.begin(),nums.end());
  6. for(int k=0;k<nums.size();k++)
  7. {
  8. if(nums[k]>target&&nums[k]>=0&&target>=0) break;
  9. if(k>0&&nums[k]==nums[k-1]) continue;
  10. for(int i=k+1;i<nums.size();i++)
  11. {
  12. if(nums[k]+nums[i]>target&&nums[k]+nums[i]>=0&&target>=0) break;
  13. if(i>k+1&&nums[i]==nums[i-1]) continue;
  14. int left= i+1,right=nums.size()-1;
  15. while(right>left)
  16. {
  17. if((long)nums[k]+nums[i]+nums[left]+nums[right]>target) right--;
  18. else if((long)nums[k]+nums[i]+nums[left]+nums[right]<target) left++;
  19. else{
  20. result.push_back({nums[k], nums[i], nums[left], nums[right]});
  21. while(right>left&&nums[right]==nums[right-1]) right--;
  22. while(right>left&&nums[left]==nums[left+1]) left++;
  23. right--;
  24. left++;
  25. }
  26. }
  27. }
  28. }
  29. return result;
  30. }
  31. };

解析:把i 的一层for循环地毯式搜索,转化为两层for循环地毯式搜索。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/很楠不爱3/article/detail/494588
推荐阅读
相关标签
  

闽ICP备14008679号