Leetcode(1) - 两数之和
题目
给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。
示例:
给定 nums = [2, 7, 11, 15], target = 9
因为 nums[0] + nums[1] = 2 + 7 = 9
所以返回 [0, 1]
初次解题分析
暴力搜索
先确定两数中的一个数,再去确定另外一个数,然后判断两数之和与Target的关系。该解法需要两层for循环,第一个for循环用于确定第一个数,第二个for循环用于确定第二个数,然后在最内部做逻辑判断。
初步代码实现
class Solution_1 {
public int[] twoSum(int[] nums, int target) {
int[] ret = new int[2];
for(int i = 0;i<nums.length;i++){
for(int j = i+1 ;j<nums.length;j++){
if(nums[i]+nums[j]==target){
ret [0] = i;
ret [1] = j;
}
}
}
return ret;
}
}
改进阶段之方法一
具体思路: 两遍HashMap
实现:
class Solution {
public int[] twoSum(int[] nums, int target) {
int[] b = new int[2];
HashMap<Integer,Integer> map = new HashMap<Integer,Integer>();
for(int i=0;i<nums.length;i++){
map.put(nums[i],i);
}
for(int j=0;j<nums.length;j++){
int a = target - nums[j];
if(map.containsKey(a) && j!=map.get(a)){
b[0] = j;
b[1] = map.get(a);
return b;
//return new int[] {j,map.get(a)};
}
}
return b;
}
}
注意:
注意if判断里的&&(短路运算符)不能被&代替,可以通过LeetCode的简单试例,但是提交时会报错。分析:&即使前面为false,运算符后面的逻辑式还是会被判断。而后面的为j != map.get(a)。很可能a是不存在的,故会报错。
改进阶段之方法二
初次代码实现的时间复杂度很高,显然不是最优解.易得知,其时间复杂度高的原因是因为进行了两次遍历.所以改进的核心就在于如何在一次遍历中就确定两个数的信息.
具体思路:
我们可以在Map中将当前数与Target值得差值作为Key,将当前数的索引作为Value。这样就同时表示了两个维度的信息,Key代表我们对另外一个数的要求,Value代表当前数的索引。
举个例子,Target为9,当前索引为0数为2,那么差值为7。只要后面数组中存在数值为7,那么两者和就为Target。
实现:
class Solution {
public int[] twoSum(int[] nums, int target) {
int[] ret = new int[]{-1,-1};
HashMap<Integer,Integer> map = new HashMap<>();
for(int i =0; i < nums.length;i++){
if(map.containsKey(nums[i])){
ret[0] = map.get(nums[i]);
ret[1] = i;
return ret;
}else{
map.put(target - nums[i],i);
}
}
return ret;
}
}
网友评论