数组任意几个元素和

来源:互联网 发布:淘宝兰亭序放大版字帖 编辑:程序博客网 时间:2024/06/05 14:25

(一)2Sum(easy)

https://leetcode.com/problems/two-sum/description/

题目:求数组中,相加得到指定结果的两个数的位置


解答:依次把数组中所有数相加比较 O(n^2)

优化:使用Hashmap, O(nlogn)

第一次犯错:Map map = new HashMap< Integer, Integer>(); 最后少了括号

代码:
public class Solution {
    public int[] twoSum(int[] nums, int target) {
        int len = nums.length;
        int[] res = new int[2];
        Map<Integer, Integer> map = new HashMap<Integer, Integer>();
        for (int i = 0; i < len; i++) {
            if (map.containsKey(target - nums[i])) {
                res[1] = i;
                res[0] = map.get(target - nums[i]);
                return res;
            }
            map.put(nums[i], i);
        }
        return res;
    }
}


(二)3Sum (Median)

https://leetcode.com/problems/3sum/description/

题目:数组数组中所有的三个数的和为0的组合,不可重复;

解答:将数组元素排序,固定一个元素,头尾指针分别指向该元素的下一个元素(次小)和数组尾(最大),依次比较并移动指针,遇到相同元素跳过;

第一次犯错:当找到满足条件组合时,没有lo++,hi++,导致死循环;
第二次犯错:只考虑两指针指向的元素不可重复,忘记考虑固定的元素同样不可重复;

代码:
public class Solution {
    public List<List<Integer>> threeSum(int[] nums) {
        List<List<Integer>> res = new LinkedList<>();
        Arrays.sort(nums);
        for (int i = 0; i < nums.length; i++) {
            while (i > 0 && i < nums.length && nums[i] == nums[i-1]) i++;
            int lo = i + 1;
            int hi = nums.length - 1;
            while (lo < hi) {
                    if (nums[lo] + nums[hi] < 0 - nums[i] ) lo++;
                    else if (nums[lo] + nums[hi] > 0 - nums[i] ) hi--;
                    else {
                            res.add(Arrays.asList(nums[i],nums[lo],nums[hi]));
                            while (lo < hi && nums[lo] == nums[lo+1]) lo++;
                            while (lo < hi && nums[hi] == nums[hi - 1]) hi--;
                            lo++;
                            hi--;
                     }       


            }
        }
        return res;
    }
}

(三)3Sum Closest (Medium)

https://leetcode.com/problems/3sum-closest/description/

题目:找出数组中三个数和最接近目标值的和
解答:现将数组排序。在数组中设三个指针:第一个指针从头开始依次遍历数组;第二个指针指向第一个指针的下一个元素;第三个指针指向数组尾部。若当前3个指针指向的元素值比目标值大,将第二个指针右移;反之,将第三个指针左移。

第一次犯错:忘记第一个指针移动后,其余两指针的值需要初始化;

代码:
public class Solution {
    public int threeSumClosest(int[] nums, int target) {
        int res = nums[0] + nums[1] + nums[2];
        
        Arrays.sort(nums);
        
        for (int i = 0; i < nums.length - 2; i++) {
             int pointer1 =  i +  1;
             int pointer2 = nums.length - 1;
            while (pointer1 < pointer2) {
                int temp = nums[i] + nums[pointer1] + nums[pointer2];
                if (temp < target) pointer1++;
                else if (temp > target) pointer2--;
                else return target;
                if (Math.abs(target - res) > Math.abs(target - temp)) res = temp;
            }
        }
        return res;
    }
}



  

阅读全文
0 0
原创粉丝点击