代码随想录算法训练营第七天 | 454.四数相加||、383.赎金信、15.三数之和、18.四数之和-做完前两个

454.四数相加Ⅱ

这个题思路不是特别好直接想出来,但是大概就是把这四个数组两两分组,前两组的记录非常重要,且要明确map的key和value分别需要记录什么,key记录两个数组的sum值,而value则记录出现过多少次,因为题目没说不能重复值,所以只要出现过的都需要记录,代表在不同位置上找到的就等于不同的!因为两个for loop下来能被记录的一定是不同位置上的。

记得创建新map的时候<>里的type要写两个啊key和value啊!别忘了而且是Integer. 然后需要熟悉map常见的几个method: get(key), getOrDefault(key, element), containskey(key), put(key, value) 这几个,本题都可以用的到,尤其是getOrDefault非常实用,因为统计一共出现过几次这种地方,没出现过的可以直接set to 0就不用担心多写一步if没出现过咋办的code了。

还有注意比较迷惑的一个点是那个第二组数组查map.getOrDefault(0-sum,0)那一行,为啥是0-sum? sum在第二组for loop里代表的是nums3和nums4的sum,而0-sum就相当于要找出满足题目要求的四个数相加等于0的那个另一半,打个比方map里存了nums1+nums2的和为4,那我们在这个0-sum里就要立志找出-4,所以和才能等于0,map.get(0-sum) (sum = -4)就能找出之前存下的4凑成对。我这个数学渣子绕了好久才把这个绕清楚。

还有需要注意因为重复的数值也要算进去,所以我们res+=的是前两组出现过的次数,比方后两组找到了一个符合的一半sum需要凑对,前两组有三个不同位置上的数值符合,那就要算成三个!所以res += map.get(...) get到出现了对少次就要加多少次的!

class Solution {
    public int fourSumCount(int[] nums1, int[] nums2, int[] nums3, int[] nums4) {
        //拆分,两两一组成对存在map里,key放a,b两组的value总和, value放出现次数
        //新建一个map,把1,2两组的sum and出现次数存在map里
        Map<Integer,Integer> map = new HashMap<>();
        for(int i : nums1){
            for(int j :nums2){
                int sum = i + j;
                map.put(sum,map.getOrDefault(sum,0)+1);
            }
        }
        //两次loop 3,4两组找出key里符合nagation of 1,2的sum的数(0-sum)记得
        //同时创一个结果int存这个符合的次数最后值返回
        int res = 0;
        for(int i : nums3){
            for(int j : nums4){
                int sum = i + j;
                res += map.getOrDefault(0 - sum,0);
            }
        }
        return res;
    }
}


383.赎金信

直接AC, 三刷了这题,再不过不合理了

需要注意for each 不接受String,需要转化成char array 用toCharArray().

时间复杂度O(n)

class Solution {
    public boolean canConstruct(String ransomNote, String magazine) {
        //creat a int arr length 26 for lowercase letters
        int [] arr = new int[26];

        //loop all letters in magazine into the arr
        for(int i : magazine.toCharArray()){
            arr[i-'a']++;
        }
        for(int i : ransomNote.toCharArray()){
            arr[i-'a']--;
        }        
        for(int i = 0; i < arr.length;i++){
            if(arr[i] < 0) return false;
        }
        return true;
    }
}


15.三数之和


18.四数之和

  • 5
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值