1、leetcode67 二进制求和
异或操作得到两数无进位相加的和
与操作 左移一位得到两数的进位
一直相加,知道进位全为0
def addBinary(self, a, b):
"""
:type a: str
:type b: str
:rtype: str
"""
x,y=int(a,2),int(b,2)
while y:
x,y=x^y,(x&y)<<1
return bin(x)[2:]
2、leetcode136 只出现一次的数字(其他数字出现两次)
思路:异或 e.g 2^2 ^3=3
def singleNumber(self, nums):
"""
:type nums: List[int]
:rtype: int
"""
if len(nums)==1:
return nums[0]
res=nums[0]
for i in range(1,len(nums)):
res=res^nums[i]
return res
3、leetcode137 只出现一次的数字(其他数字出现三次)
设置三个变量 one two three
出现一次 one=1 two=0 three=0
出现两次 one=0 two=1 three=0
出现三次 one=1 two=1 three=1 这时候three得到的是出现三次的数 one和two减去这部分的内容
返回one 剩下的就是只出现一次的数字
def singleNumber(self, nums: List[int]) -> int:
one,two,three=0,0,0
for num in nums:
two|=num&one
one^=num
three=one&two
one&=~three
two&=~three
return one
leetcode260 只出现一次的数字(有两个数字出现一次,其他出现两次)
异或计算:最后剩下的是两个只出现一次的数字(x和y)的无进位的和ans
找到一个数最右边的1:ans&(-ans)
最右边的1来自x或y其中的某一个
再用异或在原数组中找到x或y
def singleNumber(self, nums: List[int]) -> List[int]:
ans=0
for num in nums:
ans^=num
diff=ans&(-ans)
x=0
for num in nums:
if num&diff:
x^=num
return [x,ans^x]
一些知识点整理:
异或:求和/作差
相同的两个数异或之后得到0
任何数和0异或都是她本身
求一个数最右边的1:
x&(-x)
-x是x取反再加1
求一个数的二进制表示有多少个1:
x&(x-1)