题目
给你一个整数数组 nums ,除某个元素仅出现 一次 外,其余每个元素都恰>出现 三次 。请你找出并返回那个只出现了一次的元素。
进阶:你的算法应该具有线性时间复杂度。 你可以不使用额外空间来实现吗?
- 输入与输出
输入:nums = [2,2,3,2]
输出:3
思路
如果不考虑 进阶 ,也就是 使用额外空间 的话,使用 哈希表 来做应该是很容易也是很快的。
- 遍历数组;
- 讲数字加入到哈希表中;
- 遍历哈希表,找到出现次数为 1 的数字。
如果 考虑不使用额外空间 的话,那么就有些麻烦了。我借鉴了这位大佬的思路,虽然没看懂。但是带进数字推导了一下。以
int[] nums = {2,2,3,2} 为例。推导过程在代码中!
代码
- 使用额外空间
class Solution {
public int singleNumber(int[] nums) {
Map<Integer,Integer> map = new HashMap<>();
for (int val : nums) {
map.put(val,map.getOrDefault(val,0)+1);
}
int res = -1;
for (Map.Entry<Integer,Integer> entry : map.entrySet()) {
if (entry.getValue() == 1) {
res = entry.getKey();
}
}
return res;
}
}
- 不使用额外空间
class Solution {
public int singleNumber(int[] nums) {
int one = 0;
int two = 0;
int three = 0;
for(int num : nums) {
one = one ^ (~two & num);
two = two ^ (~one & num);
three = three ^ (~two & num);
}
return one;
}
// 0 ^ (~0 & 2) = 2
// 0 ^ (~2 & 2) = 0
// 0 ^ (~0 & 2) = 0
// 2 ^ (~0 & 2) = 0
// 0 ^ (~0 & 2) = 2
// 0 ^ (~2 & 2) = 0
// 0 ^ (~2 & 3) = 3
// 2 ^ (~3 & 3) = 很大
// 0 ^ (~(~3 & 3) & 3) = 0
}