題目:
Given an array of integers, find two numbers such that they add up to a specific target number.
The function twoSum should return indices of the two numbers such that they add up to the target, where index1 must be less than index2. Please note that your returned answers (both index1 and index2) are not zero-based.
You may assume that each input would have exactly one solution.
Input: numbers={2, 7, 11, 15}, target=9
Output: index1=1, index2=2
題解:
這道題也是比較經典處理陣列的,有以下兩個思路。
思路1:
利用HashMap,把target-numbers[i]的值放入hashmap中,value存index。遍歷陣列時,檢查hashmap中是否已經存能和自己加一起等於target的值存在,存在的話把index取出,連同自己的index也出去,加1(index要求從1開始)後存入結果陣列中返回。如果不存在的話,把自己的值和index存入hashmap中繼續遍歷。由於只是一遍遍歷陣列,時間複雜度為O(n)。
程式碼如下:
2 int [] res = new int[2];
3 if(numbers==null||numbers.length<2)
4 return res;
5 HashMap<Integer,Integer> map = new HashMap<Integer,Integer>();
6 for(int i = 0; i < numbers.length; i++){
7 if(!map.containsKey(target-numbers[i])){
8 map.put(numbers[i],i);
9 }else{
10 res[0]= map.get(target-numbers[i])+1;
11 res[1]= i+1;
12 break;
13 }
14 }
15 return res;
16 }
思路2:
又碰到敏感的關鍵字array和target,自然而然想到二分查詢法。但是這道題不能像傳統二分查詢法那樣捨棄一半在另外一半查詢,需要一點點挪low和high指標,所以時間複雜度為O(n)。
首先先將整個list拷貝並排序,使用Arrays.Sort()函式,時間複雜度O(nlogn)
然後利用二分查詢法,判斷target和numbers[low]+numbers[high]。
target == numbers[low]+numbers[high], 記錄copy[low]和copy[high];
target > numbers[low]+numbers[high],說明最大的和最小的加一起還小於target,所以小值要取大一點,即low++;
target > numbers[low]+numbers[high], 說明最大的和最小的加一起大於target,那麼大值需要往下取一點,即high--。
再把找到的兩個合格值在原list中找到對應的index,返回即可。
總共的時間複雜度為O(n+nlogn+n+n) = O(nlogn)。
程式碼如下:
2 int [] res = new int[2];
3 if(numbers==null||numbers.length<2)
4 return res;
5
6 //copy original list and sort
7 int[] copylist = new int[numbers.length];
8 System.arraycopy(numbers, 0, copylist, 0, numbers.length);
9 Arrays.sort(copylist);
10
11 int low = 0;
12 int high = copylist.length-1;
13
14 while(low<high){
15 if(copylist[low]+copylist[high]<target)
16 low++;
17 else if(copylist[low]+copylist[high]>target)
18 high--;
19 else{
20 res[0]=copylist[low];
21 res[1]=copylist[high];
22 break;
23 }
24 }
25
26 //find index from original list
27 int index1 = -1, index2 = -1;
28 for(int i = 0; i < numbers.length; i++){
29 if(numbers[i] == res[0]&&index1==-1)
30 index1 = i+1;
31 else if(numbers[i] == res[1]&&index2==-1)
32 index2 = i+1;
33 }
34 res[0] = index1;
35 res[1] = index2;
36 Arrays.sort(res);
37 return res;
38 }
Reference:
http://blog.csdn.net/linhuanmars/article/details/19711387
http://blog.csdn.net/likecool21/article/details/10504885