提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
一、题目
1.两数之和
给定一个整数数组 nums 和一个整数目标值 target,请你在该数组中找出 和为目标值 target 的那 两个 整数,并返回它们的数组下标。
你可以假设每种输入只会对应一个答案。但是,数组中同一个元素在答案里不能重复出现。
你可以按任意顺序返回答案。
示例 1:
输入:nums = [2,7,11,15], target = 9
输出:[0,1]
解释:因为 nums[0] + nums[1] == 9 ,返回 [0, 1] 。
示例 2:
输入:nums = [3,2,4], target = 6
输出:[1,2]
示例 3:
输入:nums = [3,3], target = 6
输出:[0,1]
二、解题思路
- 暴力,遍历所有数组元素,找出相加之和 = target 的两个元素并返回其下标。
- 哈希。将 a+b=target 这个问题转换为,已知a,在数组中a的左边(也可以往右侧找)找b,其中 b=target-a。创建一个哈希表,对于每一个 a,我们首先查询哈希表中是否存在 target-a,然后将 a 插入到哈希表中,即可保证不会让 a 和自己匹配。
三、代码
1.C
a.暴力
/**
* Note: The returned array must be malloced, assume caller calls free().
*/
int* twoSum(int* nums, int numsSize, int target, int* returnSize){
int i,j;
int* result;
*returnSize=2;
for(i=0;i<numsSize-1;i++){
for(j=i+1;j<numsSize;j++){
if(nums[i]+nums[j]==target){
result=(int*)malloc(sizeof(int)*2);
result[0]=i;
result[1]=j;
return result;
}
}
}
return 0;
}
b.哈希
/**
* Note: The returned array must be malloced, assume caller calls free().
*/
struct hash{
int key;
int value;
UT_hash_handle hh;
};
int* twoSum(int* nums, int numsSize, int target, int* returnSize) {
struct hash *idx=NULL;
int i;
for(i=0; ;i++)
{
struct hash *e;
int t=target-nums[i];
HASH_FIND_INT(idx,&t,e);
if(e)
{
int *result=malloc(2*sizeof(int));
*returnSize=2;
result[0]=e->value;
result[1]=i;
return result;
}
e=malloc(sizeof(struct hash));
e->key=nums[i];
e->value=i;
HASH_ADD_INT(idx,key,e);
}
}
2.C++
a.暴力
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
int n=nums.size();
int i,j;
for(i=0;i<n-1;i++)
{
for(j=i+1;j<n;j++)
{
if(nums[i]+nums[j]==target)
{
return {i,j};
}
}
}
return {};
}
};
b.哈希
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
unordered_map<int, int> hashtable;
int n = nums.size();
int i;
for (i = 0; i < n; i++)
{
auto it = hashtable.find(target - nums[i]);
if(it != hashtable.end())
{
return {it->second, i};
}
hashtable[nums[i]]=i;
}
return {};
}
};
3. python
a.暴力
class Solution:
def twoSum(self, nums: List[int], target: int) -> List[int]:
n=len(nums)
for i in range(n):
for j in range(i+1,n):
if nums[i]+nums[j]==target:
return [i,j]
return []
b.哈希
class Solution:
def twoSum(self, nums: List[int], target: int) -> List[int]:
hashtble=dict()
for i,num in enumerate(nums):
if target-num in hashtble:
return [hashtble[target-num],i]
hashtble[nums[i]] = i
return []
四、总结
1.暴力
时间复杂度:O(N^2),其中 N 是数组中的元素数量。最坏情况下数组中任意两个数都要被匹配一次。
空间复杂度:O(1)。
2.哈希
时间复杂度:O(N),其中 N是数组中的元素数量。对于每一个元素 x,我们可以 O(1) 地寻找 target - a。
空间复杂度:O(N),其中 N 是数组中的元素数量。主要为哈希表的开销。
哈希相当于“用空间换时间”。
这道题的难度是简单,用暴力求解完全可以解决,解法也很容易想到。哈希解法相当于利用哈希表作为工具,减少遍历的次数,从而减少程序运行时间,提高效率。