https://leetcode-cn.com/problems/WGki4K/
给你一个整数数组 nums ,除某个元素仅出现 一次 外,其余每个元素都恰出现 三次 。请你找出并返回那个只出现了一次的元素。
示例1
输入:nums = [2,2,3,2]
输出:3
示例2
输入:nums = [0,1,0,1,0,1,100]
输出:100
提示
1 <= nums.length <= 3 * 10^4
-2^31 <= nums[i] <= 2^31 - 1
nums 中,除某个元素仅出现 一次 外,其余每个元素都恰出现 三次
1、切片法
class Solution:
def singleNumber(self, nums: List[int]) -> int:
for i in range(len(nums)):
if nums[i] not in nums[i+1:] and nums[i] not in nums[0:i]:
return nums[i]
return -1
2、字典法
class Solution:
def singleNumber(self, nums: List[int]) -> int:
dic = {}
for i in nums:
if i in dic.keys():
dic[i] += 1
else:
dic[i] = 1
for k, v in dic.items():
if v == 1:
return k
return -1
3、哈希表
collections.defaultdict()—定义默认字典
其实defaultdict 就是一个字典,只不过python自动的为它的键赋了一个初始值。这也就是说,你不显示的为字典的键赋初值python不会报错。
class Solution:
def singleNumber(self, nums: List[int]) -> int:
from collections import defaultdict
record = defaultdict(int)
for i, x in enumerate(nums):
record[x] += 1
for k, v in record.items():
if v == 1:
return k
return -1
4、转成set
2*tar = 3 * sum(set(nums)) - sum(nums)
class Solution:
def singleNumber(self, nums: List[int]) -> int:
return (3*(sum(set(nums))) - sum(nums)) // 2
5、位运算
这里要注意下由于Python是无符号位的二进制,所以需要对最高位进行判断。
若为1则表示负数,需要对ret进行减等操作。
class Solution:
def singleNumber(self, nums: List[int]) -> int:
res = 0 # 1 初始化res=0
for i in range(32): # 循环32位
bit = 1 << i # 第i位的bit,比如i=1时,bit = 2^1=2
bitnum = 0 # 循环数组计算第i位之和
for num in nums:
if num & bit != 0:
bitnum += 1
if bitnum % 3 != 0: # 对3取余不为0的位数进行异或
if i == 31: # 判断是否为负数,最高位为1则为负数
res -= bit
else:
res ^= bit # 按位异或
return res
1、初始化res = 0
2、循环32位二进制数i
3、bit = 1 << i表示当前位数,i = 1时,bit = 2^1=2
bitnum = 0 循环数组第i位之和
num & bit != 0 表示num在第i位为1,bitnum+=1
4、bitnum对3取余数
余数为1,表明当前位在要找的数里为1,进行按位异或
判断是否为负数,若最高位为1则为负数,需要进行减等操作
^ 按位异或
比如5^6=3
101 5
110 6
011 3异或结果