两数之和(001)
先看代码
class Solution {
HashMap<Integer, Integer> map = new HashMap<>();
public int[] twoSum(int[] nums, int target) {
int n = nums.length;
for (int i = 0; i < n; i++){
if (map.containsKey(nums[i])){
return new int[]{ map.get(nums[i]), i};
}
map.put(target - nums[i], i);
}
return new int[]{0,0};
}
}
- 分析
对枚举的每一个num进行target - num处理, 来服务后来的num
- 感悟
充分利用每一次枚举, 对强相关性数据进行关联
字母异位词分组(049)
先看代码
class Solution {
public List<List<String>> groupAnagrams(String[] strs) {
HashMap<String, List<String>> map = new HashMap<>();
for (String str : strs){
char[] temp = str.toCharArray();
Arrays.sort(temp);
String sortString = new String(temp);
List<String> list = map.getOrDefault(sortString, new ArrayList<>());
list.add(str);
map.put(sortString,list);
}
return new ArrayList<>(map.values());
}
}
- 分析
根据分组依据(同组数据字符串包含相同的字符)对每个str进行字符排序得到temp
以temp作为分组依据
- 感悟
在需要对所有值进行处理时 O(n)必定为最优时间复杂度, 此题不可避免的要对 无序str进行处理 排序(* k * log k) 如果对str进行枚举再组合(3a4b1c5m)的话有 (* k * 26)
log k < 26显然排序算法更优
最长连续序列(128)
先看代码
class Solution {
public int longestConsecutive(int[] nums) {
int res = 0;
HashSet<Integer> set = new HashSet<>();
for (int num : nums){
set.add(num);
}
for (int num : set){
if (set.contains(num-1)){
continue;
}
int numEnd = num +1;
while (set.contains(numEnd)){
numEnd++;
}
res = Math.max(res , numEnd - num);
}
return res;
}
}
- 分析
将nums放入HashSet中,再通过找到连续序列的起始点,计算连续序列长度取最大值
- 感悟
此题的时间复杂度为O(n + k),其中k = n - 重复数字,而二分排序的时间复杂度为O(n log n + n)
但二分排序的效率却高于哈希,可能是因为哈希需要进行哈希计算、解决哈希冲突, 及哈希扩容
这一系列琐事吧