欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

关于力扣第一题 ---两数之和(多方法)

程序员文章站 2022-05-10 13:10:24
题目描述: 给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。 你可以假设每种输入只会对应一个答案。但是,你不能重复利用这个数组中同样的元素。 示例: 2.利用indexOf, Array 的 indexOf 方法实际上是对数 ......

题目描述:

给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。

你可以假设每种输入只会对应一个答案。但是,你不能重复利用这个数组中同样的元素。

示例:

给定 nums = [2, 7, 11, 15], target = 9

因为 nums[0] + nums[1] = 2 + 7 = 9
所以返回 [0, 1]
1.穷举法,两次遍历,暴力计算。使用第1个数与后面的每个数之和判断是否等于目标值、再用第2个数字做同样的操作,直到完全相等,返回索引值+1:
两个循环,时间复杂度为o(n*n)
 1 var twosum = function(nums, target) {
 2     for(var i = 0; i < nums.length - 1; i++){
 3         for(var j = i + 1; j < nums.length; j++) {
 4         if (nums[i] + nums[j] == target) {
 5             var arr = [];
 6             arr.push(i,j);
 7             return arr;
 8         }
 9       }
10    }
11 };
 

2.利用indexof, array 的 indexof 方法实际上是对数组再遍历一次,写法上有优化,但是实际时间复杂度还是o(n*n):

 1 let twosum = function(nums, target) {
 2     let a, b;
 3     for(let i = 0; i < nums.length; i++) {
 4         b = nums.indexof(target - nums[i]);
 5         if(b > -1 && b !== i) {
 6             a = i;
 7             break;
 8         }
 9     }
10     return [a, b];
11 };

 

3.使用对象索引(时间复杂度低):

创建一个对象,并给它赋值,对象的键值是我们想要检索的值,对象的值是在数组中的索引。

解题思路:构造了arr{ key:value} 对象。将target-nums[i] 差值放在arr{ }对象中,并存储其位置i。然后每次就在arr{ }对象中找有没有对应的数即可。

1 var twosum = function(nums, target) {
2     var arr = {};
3     for (var i = 0; i < nums.length; i++) {
4         if (typeof(arr[nums[i]]) !== "undefined"){
5             return [arr[nums[i]], i];                        
6         }                         
7         arr[target - nums[i]] = i;
8     }
9 };

 

4.经典解题方法,排序+二分搜索

如果这个数据是有序的,那么我们很容易联想到使用二分搜索法,可以每次判断target-num[i]对应的值是否在num[i+1:]中,这个时候算法的复杂度变成了o(nlogn)

 1 var twosum = function getsum(arr,sum) {
 2     if(arr == '' || arr.length == 0){
 3         return false;
 4     }
 5     // arr.sort((a,b) => { return a-b });  如果是无序数组可先转为有序数组再使用二分搜索法
 6     var left = 0, right = arr.length -1;
 7     while(left < right){
 8         if(arr[left] + arr[right] > sum){
 9             right--;
10         }
11         else if(arr[left] + arr[right] < sum){
12             left++;
13         }
14         else{
15             return [left,right]; 
16             left++;
17             right--;
18         }
19     }
20 }

 

5.hash方法,在所给数组中查找依次查找与当前值所对应的目标值是否存在,如果存在则记录当前index值。

 1 const twosum = function(nums, target) {
 2    // 用于记录数组nums的长度
 3     const length = nums.length;
 4     // 实例化一个map对象
 5     let hash = new map();
 6     let index = 0;
 7     for (index = 0; index < length; index++) {
 8         // 设置 hashmap 的 <key, value>,用于后面比较取值
 9         hash.set(nums[index], index);
10     }
11  
12  
13     // 遍历数组中的每一个数,求出另一个与其相加可以满足条件的数的值,存储在 @param numtofind 中
14     let numtofind;
15     for( index = 0; index < length; index++) {
16          numtofind = target - nums[index];
17          // 查询 hashmap 中对应的值是否有对应的index,而且不能是当前数的下标(防止出现 3 + 3 = 6,但数组nums中只有一个3这样的情况)
18          if (hash.has(numtofind) && index !== hash.get(numtofind)) {
19               return [index, hash.get(numtofind)];
20          }
21      }
22 };