第一题
454.四数相加
class Solution {
public:
int fourSumCount(vector<int>& nums1, vector<int>& nums2, vector<int>& nums3, vector<int>& nums4) {
unordered_map<int,int> myset;
int count = 0;
for(int a : nums1){
for(int b :nums2){
myset[a+b]++;
}
}
for(int c:nums3){
for(int d :nums4){
if(myset.find(0-c-d) != myset.end()){
count +=myset[0-c-d];
}
}
}
return count;
}
};
主要遇到一个小问题,find找的是键(第一个int),myset[0-c-d]是对应键的值(即第二个int),差点还用了myset.second.
383.赎金信
class Solution {
public:
bool canConstruct(string ransomNote, string magazine) {
unordered_map<char,int> map;
for(int i = 0;i <magazine.size();i++){
map[magazine[i]]++;
}
for(int i = 0;i<ransomNote.size();i++){
map[ransomNote[i]]--;
if(map[ransomNote[i]] < 0) return false;
}
// for(unordered_map<char,int>::iterator it = map.begin();it != map.end();it++){
// if(it ->second < 0) return false;
// }
return true;
}
};
试了下用map写,之前给的方案使用数组直接计算,对比了下自己的方法确实慢了许多(一倍),内存倒是差不多大小,上面的代码里标注的是自己写的对比方法,等于一共用了三个for 实际上两个就可以了(因为在第二个for里只要出现不满足条件的就可以直接return 完全不需要继续计算下去了)
15.三数之和
class Solution {
public:
vector<vector<int>> threeSum(vector<int>& nums) {
sort(nums.begin(),nums.end());
vector<vector<int>> result;
for(int i =0 ;i <nums.size();i++){
if(nums[i] > 0){
break;
}
if ( i >0 && nums[i] == nums[i - 1]){
continue;
}
int left = i + 1;
int right =nums.size() - 1;
while(right >left){
if(nums[left]+nums[right]+nums[i] > 0){
right--;
}else if(nums[left]+nums[right]+nums[i] < 0){
left++;
}else{
result.push_back(vector<int>{nums[i] , nums[left] , nums[right]});
while(right > left && nums[left] == nums[left + 1]){left ++;}
while(right > left && nums[right] == nums[right - 1]){right --;}
right--;
left ++;
}
}
}
return result;
}
};
主要错误
1.第一个continue的条件必须要满足i>0 不然会越界报错。
2.最后两个的判定条件是while 不是if 即如果相等就一直++和--
3.while里少了right>left的条件判断。每次++ --都要判断,如果不满足直接跳出循环。
18.四数之和
class Solution {
public:
vector<vector<int>> fourSum(vector<int>& nums, int target) {
vector<vector<int>> result;
sort(nums.begin(),nums.end());
if (nums.size()< 4) return result;
for(int i = 0 ;i <nums.size()-3;i++){
if((long)nums[i] + nums[i+1]+nums[i+2]+nums[i+3] >target)
break;
if(i > 0 && nums[i] ==nums[i-1] ) continue;
for(int j =i + 1;j < nums.size()-2; j++){
if(j> i + 1 && nums[j] ==nums[j-1]) continue;
int left = j + 1;
int right = nums.size() - 1;
while(left<right){
long sum =(long) nums[i] + nums[j] + nums[left] + nums[right];
if(sum > target) right--;
else if(sum < target) left ++;
else{
result.push_back(vector<int>{nums[i], nums[j],nums[left],nums[right]});
while(right > left && nums[left] == nums[left + 1]) left++;
while(right > left && nums[right] == nums[right - 1]) right--;
left++;
right--;
}
}
}
}
return result;
}
};
1,。只判断了i和left,right的去重,没考虑j的去重,还有结果超过范围了,需要用long表示
2.j的判断条件时j>i+1