问题描述:两数之和
给定一个整数数组 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]
- 解释 :
nums[1] + nums[2] == 6
,返回[1, 2]
。
示例 3
- 输入 :
nums = [3,3], target = 6
- 输出 :
[0,1]
- 解释 :
nums[0] + nums[1] == 6
,返回[0, 1]
。
约束条件
2 <= nums.length <= 10⁴
-10⁹ <= nums[i] <= 10⁹
-10⁹ <= target <= 10⁹
- 只会存在一个有效答案
进阶要求
你能想出一个时间复杂度小于 O(n²) 的算法吗?
解法思路
1. 暴力枚举(Brute Force)
- 时间复杂度: O(n²)
- 空间复杂度: O(1)
- 思路 :
- 使用双重循环,遍历所有可能的两个数的组合。
- 检查它们的和是否等于
target
,如果找到则返回下标。
2. 哈希表优化(Optimal Solution)
- 时间复杂度: O(n)
- 空间复杂度: O(n)
- 思路 :
- 使用哈希表(如
unordered_map
)存储{value: index}
。 - 遍历数组,对于每个元素
nums[i]
,计算complement = target - nums[i]
。 - 检查
complement
是否在哈希表中:- 如果存在,直接返回
{map[complement], i}
。 - 否则,将当前
nums[i]
存入哈希表。
- 如果存在,直接返回
- 使用哈希表(如
代码实现
暴力枚举(C++)
cpp
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
// 暴力枚举
for(int i = 0; i < nums.size(); i++){
for(int j = i + 1; j < nums.size(); j++){
if(nums[i] + nums[j] == target){
return {i, j};
}
}
}
return {}; // 理论上题目保证有解,但最好添加默认返回值
}
};
哈希表优化(C++)
cpp
总结
方法 | 时间复杂度 | 空间复杂度 | 适用情况 |
---|---|---|---|
暴力枚举 | O(n²) | O(1) | 数据量较小 |
哈希表优化 | O(n) | O(n) | 数据量较大 |
推荐使用哈希表优化解法,因为它显著降低了时间复杂度,适用于较大的输入规模。